2 * Direct3D state management
4 * Copyright 2006 Stefan Dösinger for CodeWeavers
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
26 #include "wined3d_private.h"
28 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
29 WINE_DECLARE_DEBUG_CHANNEL(d3d_shader);
31 #define GLINFO_LOCATION ((IWineD3DImpl *)(stateblock->wineD3DDevice->wineD3D))->gl_info
33 static void state_nogl(DWORD state, IWineD3DStateBlockImpl *stateblock) {
34 /* Used for states which are not mapped to a gl state as-is, but used somehow different,
35 * e.g as a parameter for drawing, or which are unimplemented in windows d3d
37 if(STATE_IS_RENDER(state)) {
38 WINED3DRENDERSTATETYPE RenderState = state - STATE_RENDER(0);
39 TRACE("(%s,%d) no direct mapping to gl\n", debug_d3drenderstate(RenderState), stateblock->renderState[RenderState]);
41 /* Shouldn't have an unknown type here */
42 FIXME("%d no direct mapping to gl of state with unknown type\n", state);
46 static void state_undefined(DWORD state, IWineD3DStateBlockImpl *stateblock) {
47 /* Print a WARN, this allows the stateblock code to loop over all states to generate a display
48 * list without causing confusing terminal output. Deliberately no special debug name here
49 * because its undefined.
51 WARN("undefined state %d\n", state);
54 static void state_fillmode(DWORD state, IWineD3DStateBlockImpl *stateblock) {
55 D3DFILLMODE Value = stateblock->renderState[WINED3DRS_FILLMODE];
59 glPolygonMode(GL_FRONT_AND_BACK, GL_POINT);
60 checkGLcall("glPolygonMode(GL_FRONT_AND_BACK, GL_POINT)");
62 case D3DFILL_WIREFRAME:
63 glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
64 checkGLcall("glPolygonMode(GL_FRONT_AND_BACK, GL_LINE)");
67 glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
68 checkGLcall("glPolygonMode(GL_FRONT_AND_BACK, GL_FILL)");
71 FIXME("Unrecognized WINED3DRS_FILLMODE value %d\n", Value);
75 static void state_lighting(DWORD state, IWineD3DStateBlockImpl *stateblock) {
78 /* Lighting is only enabled if Vertex normals are passed by the application,
79 * but lighting does not affect the stream sources, so it is not grouped for performance reasons.
80 * This state reads the decoded vertex decl, so if it is dirty don't do anything. The
81 * vertex declaration appplying function calls this function for updating
84 if(isStateDirty(stateblock->wineD3DDevice, STATE_VDECL)) {
88 normals = stateblock->wineD3DDevice->strided_streams.u.s.normal.lpData != NULL ||
89 stateblock->wineD3DDevice->strided_streams.u.s.normal.VBO != 0;
91 if (stateblock->renderState[WINED3DRS_LIGHTING] && normals) {
92 glEnable(GL_LIGHTING);
93 checkGLcall("glEnable GL_LIGHTING");
95 glDisable(GL_LIGHTING);
96 checkGLcall("glDisable GL_LIGHTING");
100 static void state_zenable(DWORD state, IWineD3DStateBlockImpl *stateblock) {
101 switch ((WINED3DZBUFFERTYPE) stateblock->renderState[WINED3DRS_ZENABLE]) {
102 case WINED3DZB_FALSE:
103 glDisable(GL_DEPTH_TEST);
104 checkGLcall("glDisable GL_DEPTH_TEST");
107 glEnable(GL_DEPTH_TEST);
108 checkGLcall("glEnable GL_DEPTH_TEST");
111 glEnable(GL_DEPTH_TEST);
112 checkGLcall("glEnable GL_DEPTH_TEST");
113 FIXME("W buffer is not well handled\n");
116 FIXME("Unrecognized D3DZBUFFERTYPE value %d\n", stateblock->renderState[WINED3DRS_ZENABLE]);
120 static void state_cullmode(DWORD state, IWineD3DStateBlockImpl *stateblock) {
121 /* TODO: Put this into the offscreen / onscreen rendering block due to device->render_offscreen */
123 /* If we are culling "back faces with clockwise vertices" then
124 set front faces to be counter clockwise and enable culling
126 switch ((WINED3DCULL) stateblock->renderState[WINED3DRS_CULLMODE]) {
127 case WINED3DCULL_NONE:
128 glDisable(GL_CULL_FACE);
129 checkGLcall("glDisable GL_CULL_FACE");
132 glEnable(GL_CULL_FACE);
133 checkGLcall("glEnable GL_CULL_FACE");
134 if (stateblock->wineD3DDevice->render_offscreen) {
136 checkGLcall("glFrontFace GL_CW");
139 checkGLcall("glFrontFace GL_CCW");
143 case WINED3DCULL_CCW:
144 glEnable(GL_CULL_FACE);
145 checkGLcall("glEnable GL_CULL_FACE");
146 if (stateblock->wineD3DDevice->render_offscreen) {
148 checkGLcall("glFrontFace GL_CCW");
151 checkGLcall("glFrontFace GL_CW");
156 FIXME("Unrecognized/Unhandled WINED3DCULL value %d\n", stateblock->renderState[WINED3DRS_CULLMODE]);
160 static void state_shademode(DWORD state, IWineD3DStateBlockImpl *stateblock) {
161 switch ((WINED3DSHADEMODE) stateblock->renderState[WINED3DRS_SHADEMODE]) {
162 case WINED3DSHADE_FLAT:
163 glShadeModel(GL_FLAT);
164 checkGLcall("glShadeModel(GL_FLAT)");
166 case WINED3DSHADE_GOURAUD:
167 glShadeModel(GL_SMOOTH);
168 checkGLcall("glShadeModel(GL_SMOOTH)");
170 case WINED3DSHADE_PHONG:
171 FIXME("WINED3DSHADE_PHONG isn't supported\n");
174 FIXME("Unrecognized/Unhandled WINED3DSHADEMODE value %d\n", stateblock->renderState[WINED3DRS_SHADEMODE]);
178 static void state_ditherenable(DWORD state, IWineD3DStateBlockImpl *stateblock) {
179 if (stateblock->renderState[WINED3DRS_DITHERENABLE]) {
181 checkGLcall("glEnable GL_DITHER");
183 glDisable(GL_DITHER);
184 checkGLcall("glDisable GL_DITHER");
188 static void state_zwritenable(DWORD state, IWineD3DStateBlockImpl *stateblock) {
189 /* TODO: Test if in d3d z writing is enabled even if ZENABLE is off. If yes,
190 * this has to be merged with ZENABLE and ZFUNC
192 if (stateblock->renderState[WINED3DRS_ZWRITEENABLE]) {
194 checkGLcall("glDepthMask(1)");
197 checkGLcall("glDepthMask(0)");
201 static void state_zfunc(DWORD state, IWineD3DStateBlockImpl *stateblock) {
202 int glParm = CompareFunc(stateblock->renderState[WINED3DRS_ZFUNC]);
206 checkGLcall("glDepthFunc");
210 static void state_ambient(DWORD state, IWineD3DStateBlockImpl *stateblock) {
212 D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_AMBIENT], col);
214 TRACE("Setting ambient to (%f,%f,%f,%f)\n", col[0], col[1], col[2], col[3]);
215 glLightModelfv(GL_LIGHT_MODEL_AMBIENT, col);
216 checkGLcall("glLightModel for MODEL_AMBIENT");
219 static void state_blend(DWORD state, IWineD3DStateBlockImpl *stateblock) {
220 int srcBlend = GL_ZERO;
221 int dstBlend = GL_ZERO;
223 /* GL_LINE_SMOOTH needs GL_BLEND to work, according to the red book, and special blending params */
224 if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE] ||
225 stateblock->renderState[WINED3DRS_EDGEANTIALIAS] ||
226 stateblock->renderState[WINED3DRS_ANTIALIASEDLINEENABLE]) {
228 checkGLcall("glEnable GL_BLEND");
231 checkGLcall("glDisable GL_BLEND");
232 /* Nothing more to do - get out */
236 switch (stateblock->renderState[WINED3DRS_SRCBLEND]) {
237 case WINED3DBLEND_ZERO : srcBlend = GL_ZERO; break;
238 case WINED3DBLEND_ONE : srcBlend = GL_ONE; break;
239 case WINED3DBLEND_SRCCOLOR : srcBlend = GL_SRC_COLOR; break;
240 case WINED3DBLEND_INVSRCCOLOR : srcBlend = GL_ONE_MINUS_SRC_COLOR; break;
241 case WINED3DBLEND_SRCALPHA : srcBlend = GL_SRC_ALPHA; break;
242 case WINED3DBLEND_INVSRCALPHA : srcBlend = GL_ONE_MINUS_SRC_ALPHA; break;
243 case WINED3DBLEND_DESTALPHA : srcBlend = GL_DST_ALPHA; break;
244 case WINED3DBLEND_INVDESTALPHA : srcBlend = GL_ONE_MINUS_DST_ALPHA; break;
245 case WINED3DBLEND_DESTCOLOR : srcBlend = GL_DST_COLOR; break;
246 case WINED3DBLEND_INVDESTCOLOR : srcBlend = GL_ONE_MINUS_DST_COLOR; break;
247 case WINED3DBLEND_SRCALPHASAT : srcBlend = GL_SRC_ALPHA_SATURATE; break;
249 case WINED3DBLEND_BOTHSRCALPHA : srcBlend = GL_SRC_ALPHA;
250 dstBlend = GL_SRC_ALPHA;
253 case WINED3DBLEND_BOTHINVSRCALPHA : srcBlend = GL_ONE_MINUS_SRC_ALPHA;
254 dstBlend = GL_ONE_MINUS_SRC_ALPHA;
257 case WINED3DBLEND_BLENDFACTOR : srcBlend = GL_CONSTANT_COLOR; break;
258 case WINED3DBLEND_INVBLENDFACTOR : srcBlend = GL_ONE_MINUS_CONSTANT_COLOR; break;
260 FIXME("Unrecognized src blend value %d\n", stateblock->renderState[WINED3DRS_SRCBLEND]);
263 switch (stateblock->renderState[WINED3DRS_DESTBLEND]) {
264 case WINED3DBLEND_ZERO : dstBlend = GL_ZERO; break;
265 case WINED3DBLEND_ONE : dstBlend = GL_ONE; break;
266 case WINED3DBLEND_SRCCOLOR : dstBlend = GL_SRC_COLOR; break;
267 case WINED3DBLEND_INVSRCCOLOR : dstBlend = GL_ONE_MINUS_SRC_COLOR; break;
268 case WINED3DBLEND_SRCALPHA : dstBlend = GL_SRC_ALPHA; break;
269 case WINED3DBLEND_INVSRCALPHA : dstBlend = GL_ONE_MINUS_SRC_ALPHA; break;
270 case WINED3DBLEND_DESTALPHA : dstBlend = GL_DST_ALPHA; break;
271 case WINED3DBLEND_INVDESTALPHA : dstBlend = GL_ONE_MINUS_DST_ALPHA; break;
272 case WINED3DBLEND_DESTCOLOR : dstBlend = GL_DST_COLOR; break;
273 case WINED3DBLEND_INVDESTCOLOR : dstBlend = GL_ONE_MINUS_DST_COLOR; break;
274 case WINED3DBLEND_SRCALPHASAT : dstBlend = GL_SRC_ALPHA_SATURATE; break;
276 case WINED3DBLEND_BOTHSRCALPHA : dstBlend = GL_SRC_ALPHA;
277 srcBlend = GL_SRC_ALPHA;
280 case WINED3DBLEND_BOTHINVSRCALPHA : dstBlend = GL_ONE_MINUS_SRC_ALPHA;
281 srcBlend = GL_ONE_MINUS_SRC_ALPHA;
284 case D3DBLEND_BLENDFACTOR : dstBlend = GL_CONSTANT_COLOR; break;
285 case D3DBLEND_INVBLENDFACTOR : dstBlend = GL_ONE_MINUS_CONSTANT_COLOR; break;
287 FIXME("Unrecognized dst blend value %d\n", stateblock->renderState[WINED3DRS_DESTBLEND]);
290 if(stateblock->renderState[WINED3DRS_EDGEANTIALIAS] ||
291 stateblock->renderState[WINED3DRS_ANTIALIASEDLINEENABLE]) {
292 glEnable(GL_LINE_SMOOTH);
293 checkGLcall("glEnable(GL_LINE_SMOOTH)");
294 if(srcBlend != GL_SRC_ALPHA) {
295 FIXME("WINED3DRS_EDGEANTIALIAS enabled, but incompatible src blending param - what to do?\n");
296 srcBlend = GL_SRC_ALPHA;
298 if(dstBlend != GL_ONE_MINUS_SRC_ALPHA) {
299 FIXME("WINED3DRS_EDGEANTIALIAS enabled, but incompatible dst blending param - what to do?\n");
300 dstBlend = GL_ONE_MINUS_SRC_ALPHA;
303 glDisable(GL_LINE_SMOOTH);
304 checkGLcall("glDisable(GL_LINE_SMOOTH)");
307 TRACE("glBlendFunc src=%x, dst=%x\n", srcBlend, dstBlend);
308 glBlendFunc(srcBlend, dstBlend);
309 checkGLcall("glBlendFunc");
312 static void state_blendfactor(DWORD state, IWineD3DStateBlockImpl *stateblock) {
315 TRACE("Setting BlendFactor to %d\n", stateblock->renderState[WINED3DRS_BLENDFACTOR]);
316 D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_BLENDFACTOR], col);
317 glBlendColor (col[0],col[1],col[2],col[3]);
318 checkGLcall("glBlendColor");
321 static void state_alpha(DWORD state, IWineD3DStateBlockImpl *stateblock) {
324 BOOL enable_ckey = FALSE;
326 IWineD3DSurfaceImpl *surf;
328 /* Find out if the texture on the first stage has a ckey set
329 * The alpha state func reads the texture settings, even though alpha and texture are not grouped
330 * together. This is to avoid making a huge alpha+texture+texture stage+ckey block due to the hardly
331 * used WINED3DRS_COLORKEYENABLE state(which is d3d <= 3 only). The texture function will call alpha
332 * in case it finds some texture+colorkeyenable combination which needs extra care.
334 if(stateblock->textures[0]) {
335 surf = (IWineD3DSurfaceImpl *) ((IWineD3DTextureImpl *)stateblock->textures[0])->surfaces[0];
336 if(surf->CKeyFlags & DDSD_CKSRCBLT) enable_ckey = TRUE;
339 if (stateblock->renderState[WINED3DRS_ALPHATESTENABLE] ||
340 (stateblock->renderState[WINED3DRS_COLORKEYENABLE] && enable_ckey)) {
341 glEnable(GL_ALPHA_TEST);
342 checkGLcall("glEnable GL_ALPHA_TEST");
344 glDisable(GL_ALPHA_TEST);
345 checkGLcall("glDisable GL_ALPHA_TEST");
346 /* Alpha test is disabled, don't bother setting the params - it will happen on the next
352 if(stateblock->renderState[WINED3DRS_COLORKEYENABLE] && enable_ckey) {
353 glParm = GL_NOTEQUAL;
356 ref = ((float) stateblock->renderState[WINED3DRS_ALPHAREF]) / 255.0f;
357 glParm = CompareFunc(stateblock->renderState[WINED3DRS_ALPHAFUNC]);
360 glAlphaFunc(glParm, ref);
361 checkGLcall("glAlphaFunc");
363 /* TODO: Some texture blending operations seem to affect the alpha test */
366 static void state_clipping(DWORD state, IWineD3DStateBlockImpl *stateblock) {
367 DWORD enable = 0xFFFFFFFF;
368 DWORD disable = 0x00000000;
370 /* TODO: Keep track of previously enabled clipplanes to avoid unneccessary resetting
371 * of already set values
374 /* If enabling / disabling all
375 * TODO: Is this correct? Doesn't D3DRS_CLIPPING disable clipping on the viewport frustrum?
377 if (stateblock->renderState[WINED3DRS_CLIPPING]) {
378 enable = stateblock->renderState[WINED3DRS_CLIPPLANEENABLE];
379 disable = ~stateblock->renderState[WINED3DRS_CLIPPLANEENABLE];
381 disable = 0xffffffff;
385 if (enable & WINED3DCLIPPLANE0) { glEnable(GL_CLIP_PLANE0); checkGLcall("glEnable(clip plane 0)"); }
386 if (enable & WINED3DCLIPPLANE1) { glEnable(GL_CLIP_PLANE1); checkGLcall("glEnable(clip plane 1)"); }
387 if (enable & WINED3DCLIPPLANE2) { glEnable(GL_CLIP_PLANE2); checkGLcall("glEnable(clip plane 2)"); }
388 if (enable & WINED3DCLIPPLANE3) { glEnable(GL_CLIP_PLANE3); checkGLcall("glEnable(clip plane 3)"); }
389 if (enable & WINED3DCLIPPLANE4) { glEnable(GL_CLIP_PLANE4); checkGLcall("glEnable(clip plane 4)"); }
390 if (enable & WINED3DCLIPPLANE5) { glEnable(GL_CLIP_PLANE5); checkGLcall("glEnable(clip plane 5)"); }
392 if (disable & WINED3DCLIPPLANE0) { glDisable(GL_CLIP_PLANE0); checkGLcall("glDisable(clip plane 0)"); }
393 if (disable & WINED3DCLIPPLANE1) { glDisable(GL_CLIP_PLANE1); checkGLcall("glDisable(clip plane 1)"); }
394 if (disable & WINED3DCLIPPLANE2) { glDisable(GL_CLIP_PLANE2); checkGLcall("glDisable(clip plane 2)"); }
395 if (disable & WINED3DCLIPPLANE3) { glDisable(GL_CLIP_PLANE3); checkGLcall("glDisable(clip plane 3)"); }
396 if (disable & WINED3DCLIPPLANE4) { glDisable(GL_CLIP_PLANE4); checkGLcall("glDisable(clip plane 4)"); }
397 if (disable & WINED3DCLIPPLANE5) { glDisable(GL_CLIP_PLANE5); checkGLcall("glDisable(clip plane 5)"); }
399 /** update clipping status */
401 stateblock->clip_status.ClipUnion = 0;
402 stateblock->clip_status.ClipIntersection = 0xFFFFFFFF;
404 stateblock->clip_status.ClipUnion = 0;
405 stateblock->clip_status.ClipIntersection = 0;
409 static void state_blendop(DWORD state, IWineD3DStateBlockImpl *stateblock) {
410 int glParm = GL_FUNC_ADD;
412 if(!GL_SUPPORT(EXT_BLEND_MINMAX)) {
413 WARN("Unsupported in local OpenGL implementation: glBlendEquation\n");
417 switch ((WINED3DBLENDOP) stateblock->renderState[WINED3DRS_BLENDOP]) {
418 case WINED3DBLENDOP_ADD : glParm = GL_FUNC_ADD; break;
419 case WINED3DBLENDOP_SUBTRACT : glParm = GL_FUNC_SUBTRACT; break;
420 case WINED3DBLENDOP_REVSUBTRACT : glParm = GL_FUNC_REVERSE_SUBTRACT; break;
421 case WINED3DBLENDOP_MIN : glParm = GL_MIN; break;
422 case WINED3DBLENDOP_MAX : glParm = GL_MAX; break;
424 FIXME("Unrecognized/Unhandled D3DBLENDOP value %d\n", stateblock->renderState[WINED3DRS_BLENDOP]);
427 TRACE("glBlendEquation(%x)\n", glParm);
428 GL_EXTCALL(glBlendEquation(glParm));
429 checkGLcall("glBlendEquation");
433 state_specularenable(DWORD state, IWineD3DStateBlockImpl *stateblock) {
434 /* Originally this used glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL,GL_SEPARATE_SPECULAR_COLOR)
435 * and (GL_LIGHT_MODEL_COLOR_CONTROL,GL_SINGLE_COLOR) to swap between enabled/disabled
436 * specular color. This is wrong:
437 * Separate specular color means the specular colour is maintained separately, whereas
438 * single color means it is merged in. However in both cases they are being used to
440 * To disable specular color, set it explicitly to black and turn off GL_COLOR_SUM_EXT
441 * NOTE: If not supported don't give FIXMEs the impact is really minimal and very few people are
445 * If register combiners are enabled, enabling / disabling GL_COLOR_SUM has no effect.
446 * Instead, we need to setup the FinalCombiner properly.
448 * The default setup for the FinalCombiner is:
450 * <variable> <input> <mapping> <usage>
451 * GL_VARIABLE_A_NV GL_FOG, GL_UNSIGNED_IDENTITY_NV GL_ALPHA
452 * GL_VARIABLE_B_NV GL_SPARE0_PLUS_SECONDARY_COLOR_NV GL_UNSIGNED_IDENTITY_NV GL_RGB
453 * GL_VARIABLE_C_NV GL_FOG GL_UNSIGNED_IDENTITY_NV GL_RGB
454 * GL_VARIABLE_D_NV GL_ZERO GL_UNSIGNED_IDENTITY_NV GL_RGB
455 * GL_VARIABLE_E_NV GL_ZERO GL_UNSIGNED_IDENTITY_NV GL_RGB
456 * GL_VARIABLE_F_NV GL_ZERO GL_UNSIGNED_IDENTITY_NV GL_RGB
457 * GL_VARIABLE_G_NV GL_SPARE0_NV GL_UNSIGNED_IDENTITY_NV GL_ALPHA
459 * That's pretty much fine as it is, except for variable B, which needs to take
460 * either GL_SPARE0_PLUS_SECONDARY_COLOR_NV or GL_SPARE0_NV, depending on
461 * whether WINED3DRS_SPECULARENABLE is enabled or not.
464 TRACE("Setting specular enable state\n");
465 /* TODO: Add to the material setting functions */
466 if (stateblock->renderState[WINED3DRS_SPECULARENABLE]) {
467 glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, (float*) &stateblock->material.Specular);
468 checkGLcall("glMaterialfv");
469 if (GL_SUPPORT(EXT_SECONDARY_COLOR)) {
470 glEnable(GL_COLOR_SUM_EXT);
472 TRACE("Specular colors cannot be enabled in this version of opengl\n");
474 checkGLcall("glEnable(GL_COLOR_SUM)");
476 if (GL_SUPPORT(NV_REGISTER_COMBINERS)) {
477 GL_EXTCALL(glFinalCombinerInputNV(GL_VARIABLE_B_NV, GL_SPARE0_PLUS_SECONDARY_COLOR_NV, GL_UNSIGNED_IDENTITY_NV, GL_RGB));
478 checkGLcall("glFinalCombinerInputNV()");
481 float black[4] = {0.0f, 0.0f, 0.0f, 0.0f};
483 /* for the case of enabled lighting: */
484 glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, &black[0]);
485 checkGLcall("glMaterialfv");
487 /* for the case of disabled lighting: */
488 if (GL_SUPPORT(EXT_SECONDARY_COLOR)) {
489 glDisable(GL_COLOR_SUM_EXT);
491 TRACE("Specular colors cannot be disabled in this version of opengl\n");
493 checkGLcall("glDisable(GL_COLOR_SUM)");
495 if (GL_SUPPORT(NV_REGISTER_COMBINERS)) {
496 GL_EXTCALL(glFinalCombinerInputNV(GL_VARIABLE_B_NV, GL_SPARE0_NV, GL_UNSIGNED_IDENTITY_NV, GL_RGB));
497 checkGLcall("glFinalCombinerInputNV()");
502 static void state_texfactor(DWORD state, IWineD3DStateBlockImpl *stateblock) {
505 /* Note the texture color applies to all textures whereas
506 * GL_TEXTURE_ENV_COLOR applies to active only
509 D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_TEXTUREFACTOR], col);
511 if (!GL_SUPPORT(NV_REGISTER_COMBINERS)) {
512 /* And now the default texture color as well */
513 for (i = 0; i < GL_LIMITS(texture_stages); i++) {
514 /* Note the WINED3DRS value applies to all textures, but GL has one
515 * per texture, so apply it now ready to be used!
517 if (GL_SUPPORT(ARB_MULTITEXTURE)) {
518 GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + i));
519 checkGLcall("glActiveTextureARB");
521 FIXME("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
524 glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, &col[0]);
525 checkGLcall("glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, color);");
528 GL_EXTCALL(glCombinerParameterfvNV(GL_CONSTANT_COLOR0_NV, &col[0]));
533 renderstate_stencil_twosided(IWineD3DStateBlockImpl *stateblock, GLint face, GLint func, GLint ref, GLuint mask, GLint stencilFail, GLint depthFail, GLint stencilPass ) {
534 #if 0 /* Don't use OpenGL 2.0 calls for now */
535 if(GL_EXTCALL(glStencilFuncSeparate) && GL_EXTCALL(glStencilOpSeparate)) {
536 GL_EXTCALL(glStencilFuncSeparate(face, func, ref, mask));
537 checkGLcall("glStencilFuncSeparate(...)");
538 GL_EXTCALL(glStencilOpSeparate(face, stencilFail, depthFail, stencilPass));
539 checkGLcall("glStencilOpSeparate(...)");
543 if(GL_SUPPORT(EXT_STENCIL_TWO_SIDE)) {
544 glEnable(GL_STENCIL_TEST_TWO_SIDE_EXT);
545 checkGLcall("glEnable(GL_STENCIL_TEST_TWO_SIDE_EXT)");
546 GL_EXTCALL(glActiveStencilFaceEXT(face));
547 checkGLcall("glActiveStencilFaceEXT(...)");
548 glStencilFunc(func, ref, mask);
549 checkGLcall("glStencilFunc(...)");
550 glStencilOp(stencilFail, depthFail, stencilPass);
551 checkGLcall("glStencilOp(...)");
552 } else if(GL_SUPPORT(ATI_SEPARATE_STENCIL)) {
553 GL_EXTCALL(glStencilFuncSeparateATI(face, func, ref, mask));
554 checkGLcall("glStencilFuncSeparateATI(...)");
555 GL_EXTCALL(glStencilOpSeparateATI(face, stencilFail, depthFail, stencilPass));
556 checkGLcall("glStencilOpSeparateATI(...)");
558 ERR("Separate (two sided) stencil not supported on this version of opengl. Caps weren't honored?\n");
563 state_stencil(DWORD state, IWineD3DStateBlockImpl *stateblock) {
564 DWORD onesided_enable = FALSE;
565 DWORD twosided_enable = FALSE;
566 GLint func = GL_ALWAYS;
567 GLint func_ccw = GL_ALWAYS;
570 GLint stencilFail = GL_KEEP;
571 GLint depthFail = GL_KEEP;
572 GLint stencilPass = GL_KEEP;
573 GLint stencilFail_ccw = GL_KEEP;
574 GLint depthFail_ccw = GL_KEEP;
575 GLint stencilPass_ccw = GL_KEEP;
577 if( stateblock->set.renderState[WINED3DRS_STENCILENABLE] )
578 onesided_enable = stateblock->renderState[WINED3DRS_STENCILENABLE];
579 if( stateblock->set.renderState[WINED3DRS_TWOSIDEDSTENCILMODE] )
580 twosided_enable = stateblock->renderState[WINED3DRS_TWOSIDEDSTENCILMODE];
581 if( stateblock->set.renderState[WINED3DRS_STENCILFUNC] )
582 if( !( func = CompareFunc(stateblock->renderState[WINED3DRS_STENCILFUNC]) ) )
584 if( stateblock->set.renderState[WINED3DRS_CCW_STENCILFUNC] )
585 if( !( func_ccw = CompareFunc(stateblock->renderState[WINED3DRS_CCW_STENCILFUNC]) ) )
587 if( stateblock->set.renderState[WINED3DRS_STENCILREF] )
588 ref = stateblock->renderState[WINED3DRS_STENCILREF];
589 if( stateblock->set.renderState[WINED3DRS_STENCILMASK] )
590 mask = stateblock->renderState[WINED3DRS_STENCILMASK];
591 if( stateblock->set.renderState[WINED3DRS_STENCILFAIL] )
592 stencilFail = StencilOp(stateblock->renderState[WINED3DRS_STENCILFAIL]);
593 if( stateblock->set.renderState[WINED3DRS_STENCILZFAIL] )
594 depthFail = StencilOp(stateblock->renderState[WINED3DRS_STENCILZFAIL]);
595 if( stateblock->set.renderState[WINED3DRS_STENCILPASS] )
596 stencilPass = StencilOp(stateblock->renderState[WINED3DRS_STENCILPASS]);
597 if( stateblock->set.renderState[WINED3DRS_CCW_STENCILFAIL] )
598 stencilFail_ccw = StencilOp(stateblock->renderState[WINED3DRS_CCW_STENCILFAIL]);
599 if( stateblock->set.renderState[WINED3DRS_CCW_STENCILZFAIL] )
600 depthFail_ccw = StencilOp(stateblock->renderState[WINED3DRS_CCW_STENCILZFAIL]);
601 if( stateblock->set.renderState[WINED3DRS_CCW_STENCILPASS] )
602 stencilPass_ccw = StencilOp(stateblock->renderState[WINED3DRS_CCW_STENCILPASS]);
604 TRACE("(onesided %d, twosided %d, ref %x, mask %x, "
605 "GL_FRONT: func: %x, fail %x, zfail %x, zpass %x "
606 "GL_BACK: func: %x, fail %x, zfail %x, zpass %x )\n",
607 onesided_enable, twosided_enable, ref, mask,
608 func, stencilFail, depthFail, stencilPass,
609 func_ccw, stencilFail_ccw, depthFail_ccw, stencilPass_ccw);
611 if (twosided_enable) {
612 renderstate_stencil_twosided(stateblock, GL_FRONT, func, ref, mask, stencilFail, depthFail, stencilPass);
613 renderstate_stencil_twosided(stateblock, GL_BACK, func_ccw, ref, mask, stencilFail_ccw, depthFail_ccw, stencilPass_ccw);
615 if (onesided_enable) {
616 glEnable(GL_STENCIL_TEST);
617 checkGLcall("glEnable GL_STENCIL_TEST");
618 glStencilFunc(func, ref, mask);
619 checkGLcall("glStencilFunc(...)");
620 glStencilOp(stencilFail, depthFail, stencilPass);
621 checkGLcall("glStencilOp(...)");
623 glDisable(GL_STENCIL_TEST);
624 checkGLcall("glDisable GL_STENCIL_TEST");
629 static void state_stencilwrite(DWORD state, IWineD3DStateBlockImpl *stateblock) {
630 glStencilMask(stateblock->renderState[WINED3DRS_STENCILWRITEMASK]);
631 checkGLcall("glStencilMask");
634 static void state_fog(DWORD state, IWineD3DStateBlockImpl *stateblock) {
635 /* TODO: Put this into the vertex type block once that is in the state table */
636 BOOL fogenable = stateblock->renderState[WINED3DRS_FOGENABLE];
637 float fogstart, fogend;
645 /* No fog? Disable it, and we're done :-) */
647 checkGLcall("glDisable GL_FOG");
650 tmpvalue.d = stateblock->renderState[WINED3DRS_FOGSTART];
651 fogstart = tmpvalue.f;
652 tmpvalue.d = stateblock->renderState[WINED3DRS_FOGEND];
655 /* Activate when vertex shaders are in the state table */
656 if(stateblock->vertexShader && ((IWineD3DVertexShaderImpl *)stateblock->vertexShader)->baseShader.function &&
657 ((IWineD3DVertexShaderImpl *)stateblock->vertexShader)->usesFog) {
658 glFogi(GL_FOG_MODE, GL_LINEAR);
659 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR)");
662 stateblock->wineD3DDevice->last_was_foggy_shader = TRUE;
664 /* DX 7 sdk: "If both render states(vertex and table fog) are set to valid modes,
665 * the system will apply only pixel(=table) fog effects."
667 else if(stateblock->renderState[WINED3DRS_FOGTABLEMODE] == D3DFOG_NONE) {
668 glHint(GL_FOG_HINT, GL_FASTEST);
669 checkGLcall("glHint(GL_FOG_HINT, GL_FASTEST)");
670 stateblock->wineD3DDevice->last_was_foggy_shader = FALSE;
672 switch (stateblock->renderState[WINED3DRS_FOGVERTEXMODE]) {
673 /* Processed vertices have their fog factor stored in the specular value. Fall too the none case.
674 * If we are drawing untransformed vertices atm, d3ddevice_set_ortho will update the fog
677 if(!stateblock->wineD3DDevice->last_was_rhw) {
678 glFogi(GL_FOG_MODE, GL_EXP);
679 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP");
680 if(GL_SUPPORT(EXT_FOG_COORD)) {
681 glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
682 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT");
688 if(!stateblock->wineD3DDevice->last_was_rhw) {
689 glFogi(GL_FOG_MODE, GL_EXP2);
690 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP2");
691 if(GL_SUPPORT(EXT_FOG_COORD)) {
692 glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
693 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT");
698 case D3DFOG_LINEAR: {
699 if(!stateblock->wineD3DDevice->last_was_rhw) {
700 glFogi(GL_FOG_MODE, GL_LINEAR);
701 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR");
702 if(GL_SUPPORT(EXT_FOG_COORD)) {
703 glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
704 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT");
710 /* Both are none? According to msdn the alpha channel of the specular
711 * color contains a fog factor. Set it in drawStridedSlow.
712 * Same happens with Vertexfog on transformed vertices
714 if(GL_SUPPORT(EXT_FOG_COORD)) {
715 glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FOG_COORDINATE_EXT);
716 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FOG_COORDINATE_EXT)\n");
717 glFogi(GL_FOG_MODE, GL_LINEAR);
718 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR)");
722 /* Disable GL fog, handle this in software in drawStridedSlow */
727 default: FIXME("Unexpected WINED3DRS_FOGVERTEXMODE %d\n", stateblock->renderState[WINED3DRS_FOGVERTEXMODE]);
730 glHint(GL_FOG_HINT, GL_NICEST);
731 checkGLcall("glHint(GL_FOG_HINT, GL_NICEST)");
732 stateblock->wineD3DDevice->last_was_foggy_shader = FALSE;
734 switch (stateblock->renderState[WINED3DRS_FOGTABLEMODE]) {
736 glFogi(GL_FOG_MODE, GL_EXP);
737 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP");
738 if(GL_SUPPORT(EXT_FOG_COORD)) {
739 glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
740 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT");
745 glFogi(GL_FOG_MODE, GL_EXP2);
746 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP2");
747 if(GL_SUPPORT(EXT_FOG_COORD)) {
748 glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
749 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT");
754 glFogi(GL_FOG_MODE, GL_LINEAR);
755 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR");
756 if(GL_SUPPORT(EXT_FOG_COORD)) {
757 glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
758 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT");
762 case D3DFOG_NONE: /* Won't happen */
764 FIXME("Unexpected WINED3DRS_FOGTABLEMODE %d\n", stateblock->renderState[WINED3DRS_FOGTABLEMODE]);
770 checkGLcall("glEnable GL_FOG");
772 glFogfv(GL_FOG_START, &fogstart);
773 checkGLcall("glFogf(GL_FOG_START, fogstart");
774 TRACE("Fog Start == %f\n", fogstart);
776 glFogfv(GL_FOG_END, &fogend);
777 checkGLcall("glFogf(GL_FOG_END, fogend");
778 TRACE("Fog End == %f\n", fogend);
781 checkGLcall("glDisable GL_FOG");
784 if (GL_SUPPORT(NV_FOG_DISTANCE)) {
785 glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_PLANE_ABSOLUTE_NV);
789 static void state_fogcolor(DWORD state, IWineD3DStateBlockImpl *stateblock) {
791 D3DCOLORTOGLFLOAT4(stateblock->renderState[WINED3DRS_FOGCOLOR], col);
792 /* Set the default alpha blend color */
793 glFogfv(GL_FOG_COLOR, &col[0]);
794 checkGLcall("glFog GL_FOG_COLOR");
797 static void state_fogdensity(DWORD state, IWineD3DStateBlockImpl *stateblock) {
802 tmpvalue.d = stateblock->renderState[WINED3DRS_FOGDENSITY];
803 glFogfv(GL_FOG_DENSITY, &tmpvalue.f);
804 checkGLcall("glFogf(GL_FOG_DENSITY, (float) Value)");
807 /* TODO: Merge with primitive type + init_materials()!! */
808 static void state_colormat(DWORD state, IWineD3DStateBlockImpl *stateblock) {
810 WineDirect3DStridedData *diffuse = &stateblock->wineD3DDevice->strided_streams.u.s.diffuse;
811 BOOL isDiffuseSupplied;
813 /* Depends on the decoded vertex declaration to read the existance of diffuse data.
814 * The vertex declaration will call this function if the fixed function pipeline is used.
816 if(isStateDirty(stateblock->wineD3DDevice, STATE_VDECL)) {
820 isDiffuseSupplied = diffuse->lpData || diffuse->VBO;
822 if (stateblock->renderState[WINED3DRS_COLORVERTEX]) {
823 TRACE("diff %d, amb %d, emis %d, spec %d\n",
824 stateblock->renderState[WINED3DRS_DIFFUSEMATERIALSOURCE],
825 stateblock->renderState[WINED3DRS_AMBIENTMATERIALSOURCE],
826 stateblock->renderState[WINED3DRS_EMISSIVEMATERIALSOURCE],
827 stateblock->renderState[WINED3DRS_SPECULARMATERIALSOURCE]);
829 if (stateblock->renderState[WINED3DRS_DIFFUSEMATERIALSOURCE] == D3DMCS_COLOR1) {
830 if (stateblock->renderState[WINED3DRS_AMBIENTMATERIALSOURCE] == D3DMCS_COLOR1) {
831 Parm = GL_AMBIENT_AND_DIFFUSE;
835 } else if (stateblock->renderState[WINED3DRS_AMBIENTMATERIALSOURCE] == D3DMCS_COLOR1) {
837 } else if (stateblock->renderState[WINED3DRS_EMISSIVEMATERIALSOURCE] == D3DMCS_COLOR1) {
839 } else if (stateblock->renderState[WINED3DRS_SPECULARMATERIALSOURCE] == D3DMCS_COLOR1) {
844 if(Parm == -1 || !isDiffuseSupplied) {
845 glDisable(GL_COLOR_MATERIAL);
846 checkGLcall("glDisable GL_COLOR_MATERIAL");
848 glColorMaterial(GL_FRONT_AND_BACK, Parm);
849 checkGLcall("glColorMaterial(GL_FRONT_AND_BACK, Parm)");
850 glEnable(GL_COLOR_MATERIAL);
851 checkGLcall("glEnable(GL_COLOR_MATERIAL)");
855 static void state_linepattern(DWORD state, IWineD3DStateBlockImpl *stateblock) {
858 WINED3DLINEPATTERN lp;
860 tmppattern.d = stateblock->renderState[WINED3DRS_LINEPATTERN];
862 TRACE("Line pattern: repeat %d bits %x\n", tmppattern.lp.wRepeatFactor, tmppattern.lp.wLinePattern);
864 if (tmppattern.lp.wRepeatFactor) {
865 glLineStipple(tmppattern.lp.wRepeatFactor, tmppattern.lp.wLinePattern);
866 checkGLcall("glLineStipple(repeat, linepattern)");
867 glEnable(GL_LINE_STIPPLE);
868 checkGLcall("glEnable(GL_LINE_STIPPLE);");
870 glDisable(GL_LINE_STIPPLE);
871 checkGLcall("glDisable(GL_LINE_STIPPLE);");
875 static void state_zbias(DWORD state, IWineD3DStateBlockImpl *stateblock) {
881 if (stateblock->renderState[WINED3DRS_ZBIAS]) {
882 tmpvalue.d = stateblock->renderState[WINED3DRS_ZBIAS];
883 TRACE("ZBias value %f\n", tmpvalue.f);
884 glPolygonOffset(0, -tmpvalue.f);
885 checkGLcall("glPolygonOffset(0, -Value)");
886 glEnable(GL_POLYGON_OFFSET_FILL);
887 checkGLcall("glEnable(GL_POLYGON_OFFSET_FILL);");
888 glEnable(GL_POLYGON_OFFSET_LINE);
889 checkGLcall("glEnable(GL_POLYGON_OFFSET_LINE);");
890 glEnable(GL_POLYGON_OFFSET_POINT);
891 checkGLcall("glEnable(GL_POLYGON_OFFSET_POINT);");
893 glDisable(GL_POLYGON_OFFSET_FILL);
894 checkGLcall("glDisable(GL_POLYGON_OFFSET_FILL);");
895 glDisable(GL_POLYGON_OFFSET_LINE);
896 checkGLcall("glDisable(GL_POLYGON_OFFSET_LINE);");
897 glDisable(GL_POLYGON_OFFSET_POINT);
898 checkGLcall("glDisable(GL_POLYGON_OFFSET_POINT);");
903 static void state_normalize(DWORD state, IWineD3DStateBlockImpl *stateblock) {
904 if (stateblock->renderState[WINED3DRS_NORMALIZENORMALS]) {
905 glEnable(GL_NORMALIZE);
906 checkGLcall("glEnable(GL_NORMALIZE);");
908 glDisable(GL_NORMALIZE);
909 checkGLcall("glDisable(GL_NORMALIZE);");
913 static void state_psize(DWORD state, IWineD3DStateBlockImpl *stateblock) {
919 /* FIXME: check that pointSize isn't outside glGetFloatv( GL_POINT_SIZE_MAX_ARB, &maxSize ); or -ve */
920 tmpvalue.d = stateblock->renderState[WINED3DRS_POINTSIZE];
921 TRACE("Set point size to %f\n", tmpvalue.f);
922 glPointSize(tmpvalue.f);
923 checkGLcall("glPointSize(...);");
926 static void state_psizemin(DWORD state, IWineD3DStateBlockImpl *stateblock) {
932 if(GL_SUPPORT(ARB_POINT_PARAMETERS)) {
933 tmpvalue.d = stateblock->renderState[WINED3DRS_POINTSIZE_MIN];
934 GL_EXTCALL(glPointParameterfARB)(GL_POINT_SIZE_MIN_ARB, tmpvalue.f);
935 checkGLcall("glPointParameterfARB(...");
937 else if(GL_SUPPORT(EXT_POINT_PARAMETERS)) {
938 tmpvalue.d = stateblock->renderState[WINED3DRS_POINTSIZE_MIN];
939 GL_EXTCALL(glPointParameterfEXT)(GL_POINT_SIZE_MIN_EXT, tmpvalue.f);
940 checkGLcall("glPointParameterfEXT(...);");
942 FIXME("WINED3DRS_POINTSIZE_MIN not supported on this opengl\n");
946 static void state_psizemax(DWORD state, IWineD3DStateBlockImpl *stateblock) {
952 if(GL_SUPPORT(ARB_POINT_PARAMETERS)) {
953 tmpvalue.d = stateblock->renderState[WINED3DRS_POINTSIZE_MAX];
954 GL_EXTCALL(glPointParameterfARB)(GL_POINT_SIZE_MAX_ARB, tmpvalue.f);
955 checkGLcall("glPointParameterfARB(...");
957 else if(GL_SUPPORT(EXT_POINT_PARAMETERS)) {
958 tmpvalue.d = stateblock->renderState[WINED3DRS_POINTSIZE_MAX];
959 GL_EXTCALL(glPointParameterfEXT)(GL_POINT_SIZE_MAX_EXT, tmpvalue.f);
960 checkGLcall("glPointParameterfEXT(...);");
962 FIXME("WINED3DRS_POINTSIZE_MAX not supported on this opengl\n");
966 static void state_pscale(DWORD state, IWineD3DStateBlockImpl *stateblock) {
967 /* TODO: Group this with the viewport */
969 * POINTSCALEENABLE controls how point size value is treated. If set to
970 * true, the point size is scaled with respect to height of viewport.
971 * When set to false point size is in pixels.
973 * http://msdn.microsoft.com/library/en-us/directx9_c/point_sprites.asp
977 GLfloat att[3] = {1.0f, 0.0f, 0.0f};
980 * Minimum valid point size for OpenGL is 1.0f. For Direct3D it is 0.0f.
981 * This means that OpenGL will clamp really small point sizes to 1.0f.
982 * To correct for this we need to multiply by the scale factor when sizes
983 * are less than 1.0f. scale_factor = 1.0f / point_size.
985 GLfloat pointSize = *((float*)&stateblock->renderState[WINED3DRS_POINTSIZE]);
986 if(pointSize > 0.0f) {
989 if(pointSize < 1.0f) {
990 scaleFactor = pointSize * pointSize;
995 if(stateblock->renderState[WINED3DRS_POINTSCALEENABLE]) {
996 att[0] = *((float*)&stateblock->renderState[WINED3DRS_POINTSCALE_A]) /
997 (stateblock->viewport.Height * stateblock->viewport.Height * scaleFactor);
998 att[1] = *((float*)&stateblock->renderState[WINED3DRS_POINTSCALE_B]) /
999 (stateblock->viewport.Height * stateblock->viewport.Height * scaleFactor);
1000 att[2] = *((float*)&stateblock->renderState[WINED3DRS_POINTSCALE_C]) /
1001 (stateblock->viewport.Height * stateblock->viewport.Height * scaleFactor);
1005 if(GL_SUPPORT(ARB_POINT_PARAMETERS)) {
1006 GL_EXTCALL(glPointParameterfvARB)(GL_POINT_DISTANCE_ATTENUATION_ARB, att);
1007 checkGLcall("glPointParameterfvARB(GL_DISTANCE_ATTENUATION_ARB, ...");
1009 else if(GL_SUPPORT(EXT_POINT_PARAMETERS)) {
1010 GL_EXTCALL(glPointParameterfvEXT)(GL_DISTANCE_ATTENUATION_EXT, att);
1011 checkGLcall("glPointParameterfvEXT(GL_DISTANCE_ATTENUATION_EXT, ...");
1013 TRACE("POINT_PARAMETERS not supported in this version of opengl\n");
1017 static void state_colorwrite(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1018 DWORD Value = stateblock->renderState[WINED3DRS_COLORWRITEENABLE];
1020 TRACE("Color mask: r(%d) g(%d) b(%d) a(%d)\n",
1021 Value & D3DCOLORWRITEENABLE_RED ? 1 : 0,
1022 Value & D3DCOLORWRITEENABLE_GREEN ? 1 : 0,
1023 Value & D3DCOLORWRITEENABLE_BLUE ? 1 : 0,
1024 Value & D3DCOLORWRITEENABLE_ALPHA ? 1 : 0);
1025 glColorMask(Value & D3DCOLORWRITEENABLE_RED ? GL_TRUE : GL_FALSE,
1026 Value & D3DCOLORWRITEENABLE_GREEN ? GL_TRUE : GL_FALSE,
1027 Value & D3DCOLORWRITEENABLE_BLUE ? GL_TRUE : GL_FALSE,
1028 Value & D3DCOLORWRITEENABLE_ALPHA ? GL_TRUE : GL_FALSE);
1029 checkGLcall("glColorMask(...)");
1031 /* depends on WINED3DRS_COLORWRITEENABLE. */
1032 if(stateblock->renderState[WINED3DRS_COLORWRITEENABLE1] != 0x0000000F ||
1033 stateblock->renderState[WINED3DRS_COLORWRITEENABLE2] != 0x0000000F ||
1034 stateblock->renderState[WINED3DRS_COLORWRITEENABLE3] != 0x0000000F ) {
1035 ERR("(WINED3DRS_COLORWRITEENABLE1/2/3,%d,%d,%d) not yet implemented. Missing of cap D3DPMISCCAPS_INDEPENDENTWRITEMASKS wasn't honored?\n",
1036 stateblock->renderState[WINED3DRS_COLORWRITEENABLE1],
1037 stateblock->renderState[WINED3DRS_COLORWRITEENABLE2],
1038 stateblock->renderState[WINED3DRS_COLORWRITEENABLE3]);
1042 static void state_localviewer(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1043 if(stateblock->renderState[WINED3DRS_LOCALVIEWER]) {
1044 glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 1);
1045 checkGLcall("glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 1)");
1047 glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 0);
1048 checkGLcall("glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 0)");
1052 static void state_lastpixel(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1053 if(stateblock->renderState[WINED3DRS_LASTPIXEL]) {
1054 TRACE("Last Pixel Drawing Enabled\n");
1056 FIXME("Last Pixel Drawing Disabled, not handled yet\n");
1060 static void state_pointsprite(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1064 /* TODO: NV_POINT_SPRITE */
1065 if (!GL_SUPPORT(ARB_POINT_SPRITE)) {
1066 TRACE("Point sprites not supported\n");
1070 if (stateblock->renderState[WINED3DRS_POINTSPRITEENABLE]) {
1076 for (i = 0; i < GL_LIMITS(texture_stages); i++) {
1077 /* Note the WINED3DRS value applies to all textures, but GL has one
1078 * per texture, so apply it now ready to be used!
1080 if (GL_SUPPORT(ARB_MULTITEXTURE)) {
1081 GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + i));
1082 checkGLcall("glActiveTextureARB");
1084 FIXME("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
1088 glTexEnvi(GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, val);
1089 checkGLcall((val?"glTexEnvi(GL_POINT_SPRITE, GL_COORD_REPLACE, GL_TRUE)":
1090 "glTexEnvi(GL_POINT_SPRITE, GL_COORD_REPLACE, GL_FALSE)"));
1094 static void state_wrap(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1096 http://www.cosc.brocku.ca/Offerings/3P98/course/lectures/texture/
1097 http://msdn.microsoft.com/archive/default.asp?url=/archive/en-us/directx9_c/directx/graphics/programmingguide/FixedFunction/Textures/texturewrapping.asp
1098 http://www.gamedev.net/reference/programming/features/rendererdll3/page2.asp
1099 Descussion that ways to turn on WRAPing to solve an opengl conversion problem.
1100 http://www.flipcode.org/cgi-bin/fcmsg.cgi?thread_show=10248
1102 so far as I can tell, wrapping and texture-coordinate generate go hand in hand,
1105 if(stateblock->renderState[WINED3DRS_WRAP0] ||
1106 stateblock->renderState[WINED3DRS_WRAP1] ||
1107 stateblock->renderState[WINED3DRS_WRAP2] ||
1108 stateblock->renderState[WINED3DRS_WRAP3] ||
1109 stateblock->renderState[WINED3DRS_WRAP4] ||
1110 stateblock->renderState[WINED3DRS_WRAP5] ||
1111 stateblock->renderState[WINED3DRS_WRAP6] ||
1112 stateblock->renderState[WINED3DRS_WRAP7] ||
1113 stateblock->renderState[WINED3DRS_WRAP8] ||
1114 stateblock->renderState[WINED3DRS_WRAP9] ||
1115 stateblock->renderState[WINED3DRS_WRAP10] ||
1116 stateblock->renderState[WINED3DRS_WRAP11] ||
1117 stateblock->renderState[WINED3DRS_WRAP12] ||
1118 stateblock->renderState[WINED3DRS_WRAP13] ||
1119 stateblock->renderState[WINED3DRS_WRAP14] ||
1120 stateblock->renderState[WINED3DRS_WRAP15] ) {
1121 ERR("(WINED3DRS_WRAP0) Texture wraping not yet supported\n");
1125 static void state_multisampleaa(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1126 if( GL_SUPPORT(ARB_MULTISAMPLE) ) {
1127 if(stateblock->renderState[WINED3DRS_MULTISAMPLEANTIALIAS]) {
1128 glEnable(GL_MULTISAMPLE_ARB);
1129 checkGLcall("glEnable(GL_MULTISAMPLE_ARB)");
1131 glDisable(GL_MULTISAMPLE_ARB);
1132 checkGLcall("glDisable(GL_MULTISAMPLE_ARB)");
1135 if(stateblock->renderState[WINED3DRS_MULTISAMPLEANTIALIAS]) {
1136 ERR("Multisample antialiasing not supported by gl\n");
1141 static void state_scissor(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1142 if(stateblock->renderState[WINED3DRS_SCISSORTESTENABLE]) {
1143 glEnable(GL_SCISSOR_TEST);
1144 checkGLcall("glEnable(GL_SCISSOR_TEST)");
1146 glDisable(GL_SCISSOR_TEST);
1147 checkGLcall("glDisable(GL_SCISSOR_TEST)");
1151 static void state_depthbias(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1157 if(stateblock->renderState[WINED3DRS_SLOPESCALEDEPTHBIAS] ||
1158 stateblock->renderState[WINED3DRS_DEPTHBIAS]) {
1159 tmpvalue.d = stateblock->renderState[WINED3DRS_SLOPESCALEDEPTHBIAS];
1160 glEnable(GL_POLYGON_OFFSET_FILL);
1161 checkGLcall("glEnable(GL_POLYGON_OFFSET_FILL)");
1162 glPolygonOffset(tmpvalue.f, *((float*)&stateblock->renderState[WINED3DRS_DEPTHBIAS]));
1163 checkGLcall("glPolygonOffset(...)");
1165 glDisable(GL_POLYGON_OFFSET_FILL);
1166 checkGLcall("glDisable(GL_POLYGON_OFFSET_FILL)");
1170 static void state_perspective(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1171 if (stateblock->renderState[WINED3DRS_TEXTUREPERSPECTIVE]) {
1172 glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
1173 checkGLcall("glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST)");
1175 glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST);
1176 checkGLcall("glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST)");
1180 static void state_stippledalpha(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1182 if (stateblock->renderState[WINED3DRS_STIPPLEDALPHA])
1183 ERR(" Stippled Alpha not supported yet.\n");
1186 static void state_antialias(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1188 if (stateblock->renderState[WINED3DRS_ANTIALIAS])
1189 ERR(" Antialias not supported yet.\n");
1192 static void state_multisampmask(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1194 if (stateblock->renderState[WINED3DRS_MULTISAMPLEMASK] != 0xFFFFFFFF)
1195 ERR("(WINED3DRS_MULTISAMPLEMASK,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_MULTISAMPLEMASK]);
1198 static void state_patchedgestyle(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1200 if (stateblock->renderState[WINED3DRS_PATCHEDGESTYLE] != D3DPATCHEDGE_DISCRETE)
1201 ERR("(WINED3DRS_PATCHEDGESTYLE,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_PATCHEDGESTYLE]);
1204 static void state_patchsegments(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1212 if (stateblock->renderState[WINED3DRS_PATCHSEGMENTS] != tmpvalue.d)
1213 ERR("(WINED3DRS_PATCHSEGMENTS,%d) not yet implemented\n", tmpvalue.d);
1216 static void state_positiondegree(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1218 if (stateblock->renderState[WINED3DRS_POSITIONDEGREE] != D3DDEGREE_CUBIC)
1219 ERR("(WINED3DRS_POSITIONDEGREE,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_POSITIONDEGREE]);
1222 static void state_normaldegree(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1224 if (stateblock->renderState[WINED3DRS_NORMALDEGREE] != D3DDEGREE_LINEAR)
1225 ERR("(WINED3DRS_NORMALDEGREE,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_NORMALDEGREE]);
1228 static void state_tessellation(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1230 if(stateblock->renderState[WINED3DRS_ENABLEADAPTIVETESSELLATION])
1231 FIXME("(WINED3DRS_ENABLEADAPTIVETESSELLATION,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_ENABLEADAPTIVETESSELLATION]);
1235 static void state_srgbwrite(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1236 if(stateblock->renderState[WINED3DRS_SRGBWRITEENABLE])
1237 ERR("Render state WINED3DRS_SRGBWRITEENABLE not yet implemented\n");
1240 static void state_seperateblend(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1242 if(stateblock->renderState[WINED3DRS_SEPARATEALPHABLENDENABLE])
1243 FIXME("(WINED3DRS_SEPARATEALPHABLENDENABLE,%d) not yet implemented\n", stateblock->renderState[WINED3DRS_SEPARATEALPHABLENDENABLE]);
1246 static void state_wrapu(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1247 if(stateblock->renderState[WINED3DRS_WRAPU]) {
1248 FIXME("Render state WINED3DRS_WRAPU not implemented yet\n");
1252 static void state_wrapv(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1253 if(stateblock->renderState[WINED3DRS_WRAPV]) {
1254 FIXME("Render state WINED3DRS_WRAPV not implemented yet\n");
1258 static void state_monoenable(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1259 if(stateblock->renderState[WINED3DRS_MONOENABLE]) {
1260 FIXME("Render state WINED3DRS_MONOENABLE not implemented yet\n");
1264 static void state_rop2(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1265 if(stateblock->renderState[WINED3DRS_ROP2]) {
1266 FIXME("Render state WINED3DRS_ROP2 not implemented yet\n");
1270 static void state_planemask(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1271 if(stateblock->renderState[WINED3DRS_PLANEMASK]) {
1272 FIXME("Render state WINED3DRS_PLANEMASK not implemented yet\n");
1276 static void state_subpixel(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1277 if(stateblock->renderState[WINED3DRS_SUBPIXEL]) {
1278 FIXME("Render state WINED3DRS_SUBPIXEL not implemented yet\n");
1282 static void state_subpixelx(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1283 if(stateblock->renderState[WINED3DRS_SUBPIXELX]) {
1284 FIXME("Render state WINED3DRS_SUBPIXELX not implemented yet\n");
1288 static void state_stippleenable(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1289 if(stateblock->renderState[WINED3DRS_STIPPLEENABLE]) {
1290 FIXME("Render state WINED3DRS_STIPPLEENABLE not implemented yet\n");
1294 static void state_bordercolor(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1295 if(stateblock->renderState[WINED3DRS_BORDERCOLOR]) {
1296 FIXME("Render state WINED3DRS_BORDERCOLOR not implemented yet\n");
1300 static void state_mipmaplodbias(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1301 if(stateblock->renderState[WINED3DRS_MIPMAPLODBIAS]) {
1302 FIXME("Render state WINED3DRS_MIPMAPLODBIAS not implemented yet\n");
1306 static void state_anisotropy(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1307 if(stateblock->renderState[WINED3DRS_ANISOTROPY]) {
1308 FIXME("Render state WINED3DRS_ANISOTROPY not implemented yet\n");
1312 static void state_flushbatch(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1313 if(stateblock->renderState[WINED3DRS_FLUSHBATCH]) {
1314 FIXME("Render state WINED3DRS_FLUSHBATCH not implemented yet\n");
1318 static void state_translucentsi(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1319 if(stateblock->renderState[WINED3DRS_TRANSLUCENTSORTINDEPENDENT]) {
1320 FIXME("Render state WINED3DRS_TRANSLUCENTSORTINDEPENDENT not implemented yet\n");
1324 static void state_extents(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1325 if(stateblock->renderState[WINED3DRS_EXTENTS]) {
1326 FIXME("Render state WINED3DRS_EXTENTS not implemented yet\n");
1330 static void state_ckeyblend(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1331 if(stateblock->renderState[WINED3DRS_COLORKEYBLENDENABLE]) {
1332 FIXME("Render state WINED3DRS_COLORKEYBLENDENABLE not implemented yet\n");
1336 /* Activates the texture dimension according to the bound D3D texture.
1337 * Does not care for the colorop or correct gl texture unit(when using nvrc)
1338 * Requires the caller to activate the correct unit before
1340 static void activate_dimensions(DWORD stage, IWineD3DStateBlockImpl *stateblock) {
1341 if(stateblock->textures[stage]) {
1342 glDisable(GL_TEXTURE_1D);
1343 checkGLcall("glDisable(GL_TEXTURE_1D)");
1344 switch(stateblock->textureDimensions[stage]) {
1346 glDisable(GL_TEXTURE_3D);
1347 checkGLcall("glDisable(GL_TEXTURE_3D)");
1348 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
1349 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
1350 glEnable(GL_TEXTURE_2D);
1351 checkGLcall("glEnable(GL_TEXTURE_2D)");
1354 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
1355 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
1356 glDisable(GL_TEXTURE_2D);
1357 checkGLcall("glDisable(GL_TEXTURE_2D)");
1358 glEnable(GL_TEXTURE_3D);
1359 checkGLcall("glEnable(GL_TEXTURE_3D)");
1361 case GL_TEXTURE_CUBE_MAP_ARB:
1362 glDisable(GL_TEXTURE_2D);
1363 checkGLcall("glDisable(GL_TEXTURE_2D)");
1364 glDisable(GL_TEXTURE_3D);
1365 checkGLcall("glDisable(GL_TEXTURE_3D)");
1366 glEnable(GL_TEXTURE_CUBE_MAP_ARB);
1367 checkGLcall("glEnable(GL_TEXTURE_CUBE_MAP_ARB)");
1371 glDisable(GL_TEXTURE_2D);
1372 checkGLcall("glDisable(GL_TEXTURE_2D)");
1373 glDisable(GL_TEXTURE_3D);
1374 checkGLcall("glDisable(GL_TEXTURE_3D)");
1375 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
1376 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
1377 glEnable(GL_TEXTURE_1D);
1378 checkGLcall("glEnable(GL_TEXTURE_1D)");
1379 /* Binding textures is done by samplers. A dummy texture will be bound */
1383 static void tex_colorop(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1384 DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / WINED3D_HIGHEST_TEXTURE_STATE;
1385 DWORD mapped_stage = stateblock->wineD3DDevice->texUnitMap[stage];
1387 TRACE("Setting color op for stage %d\n", stage);
1389 if (stateblock->pixelShader && stateblock->wineD3DDevice->ps_selected_mode != SHADER_NONE &&
1390 ((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.function) {
1391 /* Using a pixel shader? Don't care for anything here, the shader applying does it */
1395 if (stage != mapped_stage) WARN("Using non 1:1 mapping: %d -> %d!\n", stage, mapped_stage);
1397 if (mapped_stage != -1) {
1398 if (GL_SUPPORT(ARB_MULTITEXTURE)) {
1399 if (mapped_stage >= GL_LIMITS(sampler_stages)) {
1400 if (stateblock->textureState[stage][WINED3DTSS_COLOROP] != WINED3DTOP_DISABLE &&
1401 stateblock->textureState[stage][WINED3DTSS_COLOROP] != 0) {
1402 FIXME("Attempt to enable unsupported stage!\n");
1406 GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
1407 checkGLcall("glActiveTextureARB");
1408 } else if (stage > 0) {
1409 WARN("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
1414 if (GL_SUPPORT(NV_REGISTER_COMBINERS)) {
1415 if(stateblock->lowest_disabled_stage > 0) {
1416 glEnable(GL_REGISTER_COMBINERS_NV);
1417 GL_EXTCALL(glCombinerParameteriNV(GL_NUM_GENERAL_COMBINERS_NV, stateblock->lowest_disabled_stage));
1419 glDisable(GL_REGISTER_COMBINERS_NV);
1422 if(stage >= stateblock->lowest_disabled_stage) {
1423 TRACE("Stage disabled\n");
1424 if (mapped_stage != -1) {
1425 /* Disable everything here */
1426 glDisable(GL_TEXTURE_1D);
1427 checkGLcall("glDisable(GL_TEXTURE_1D)");
1428 glDisable(GL_TEXTURE_2D);
1429 checkGLcall("glDisable(GL_TEXTURE_2D)");
1430 glDisable(GL_TEXTURE_3D);
1431 checkGLcall("glDisable(GL_TEXTURE_3D)");
1432 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
1433 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
1439 if (mapped_stage != -1) activate_dimensions(stage, stateblock);
1441 /* Set the texture combiners */
1442 if (GL_SUPPORT(NV_REGISTER_COMBINERS)) {
1443 set_tex_op_nvrc((IWineD3DDevice *)stateblock->wineD3DDevice, FALSE, stage,
1444 stateblock->textureState[stage][WINED3DTSS_COLOROP],
1445 stateblock->textureState[stage][WINED3DTSS_COLORARG1],
1446 stateblock->textureState[stage][WINED3DTSS_COLORARG2],
1447 stateblock->textureState[stage][WINED3DTSS_COLORARG0],
1450 set_tex_op((IWineD3DDevice *)stateblock->wineD3DDevice, FALSE, stage,
1451 stateblock->textureState[stage][WINED3DTSS_COLOROP],
1452 stateblock->textureState[stage][WINED3DTSS_COLORARG1],
1453 stateblock->textureState[stage][WINED3DTSS_COLORARG2],
1454 stateblock->textureState[stage][WINED3DTSS_COLORARG0]);
1458 static void tex_alphaop(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1459 DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / WINED3D_HIGHEST_TEXTURE_STATE;
1460 DWORD mapped_stage = stateblock->wineD3DDevice->texUnitMap[stage];
1462 TRACE("Setting alpha op for stage %d\n", stage);
1463 /* Do not care for enabled / disabled stages, just assign the settigns. colorop disables / enables required stuff */
1464 if (mapped_stage != -1) {
1465 if (GL_SUPPORT(ARB_MULTITEXTURE)) {
1466 if (stage >= GL_LIMITS(sampler_stages)) {
1467 if (stateblock->textureState[stage][WINED3DTSS_COLOROP] != WINED3DTOP_DISABLE &&
1468 stateblock->textureState[stage][WINED3DTSS_COLOROP] != 0) {
1469 FIXME("Attempt to enable unsupported stage!\n");
1473 GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
1474 checkGLcall("glActiveTextureARB");
1475 } else if (stage > 0) {
1476 /* We can't do anything here */
1477 WARN("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
1482 TRACE("Setting alpha op for stage %d\n", stage);
1483 if (GL_SUPPORT(NV_REGISTER_COMBINERS)) {
1484 set_tex_op_nvrc((IWineD3DDevice *)stateblock->wineD3DDevice, TRUE, stage,
1485 stateblock->textureState[stage][WINED3DTSS_ALPHAOP],
1486 stateblock->textureState[stage][WINED3DTSS_ALPHAARG1],
1487 stateblock->textureState[stage][WINED3DTSS_ALPHAARG2],
1488 stateblock->textureState[stage][WINED3DTSS_ALPHAARG0],
1491 set_tex_op((IWineD3DDevice *)stateblock->wineD3DDevice, TRUE, stage, stateblock->textureState[stage][WINED3DTSS_ALPHAOP],
1492 stateblock->textureState[stage][WINED3DTSS_ALPHAARG1],
1493 stateblock->textureState[stage][WINED3DTSS_ALPHAARG2],
1494 stateblock->textureState[stage][WINED3DTSS_ALPHAARG0]);
1498 static void transform_texture(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1499 DWORD texUnit = state - STATE_TRANSFORM(WINED3DTS_TEXTURE0);
1501 if (GL_SUPPORT(ARB_MULTITEXTURE)) {
1502 if(texUnit >= GL_LIMITS(sampler_stages)) {
1505 GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + stateblock->wineD3DDevice->texUnitMap[texUnit]));
1506 checkGLcall("glActiveTextureARB");
1507 } else if (texUnit > 0) {
1508 /* We can't do anything here */
1509 WARN("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
1513 set_texture_matrix((float *)&stateblock->transforms[WINED3DTS_TEXTURE0 + texUnit].u.m[0][0],
1514 stateblock->textureState[texUnit][WINED3DTSS_TEXTURETRANSFORMFLAGS],
1515 (stateblock->textureState[texUnit][WINED3DTSS_TEXCOORDINDEX] & 0xFFFF0000) != WINED3DTSS_TCI_PASSTHRU);
1519 static void loadVertexData(IWineD3DStateBlockImpl *stateblock, WineDirect3DVertexStridedData *sd);
1521 static void tex_coordindex(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1522 DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / WINED3D_HIGHEST_TEXTURE_STATE;
1523 DWORD mapped_stage = stateblock->wineD3DDevice->texUnitMap[stage];
1525 if (mapped_stage == -1) {
1526 TRACE("No texture unit mapped to stage %d. Skipping texture coordinates.\n", stage);
1530 if (GL_SUPPORT(ARB_MULTITEXTURE)) {
1531 if(stage >= GL_LIMITS(sampler_stages)) {
1534 GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
1535 checkGLcall("glActiveTextureARB");
1536 } else if (stage > 0) {
1537 /* We can't do anything here */
1538 WARN("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
1542 /* Values 0-7 are indexes into the FVF tex coords - See comments in DrawPrimitive
1544 * FIXME: From MSDN: The WINED3DTSS_TCI_* flags are mutually exclusive. If you include
1545 * one flag, you can still specify an index value, which the system uses to
1546 * determine the texture wrapping mode.
1547 * eg. SetTextureStageState( 0, WINED3DTSS_TEXCOORDINDEX, WINED3DTSS_TCI_CAMERASPACEPOSITION | 1 );
1548 * means use the vertex position (camera-space) as the input texture coordinates
1549 * for this texture stage, and the wrap mode set in the WINED3DRS_WRAP1 render
1550 * state. We do not (yet) support the WINED3DRENDERSTATE_WRAPx values, nor tie them up
1551 * to the TEXCOORDINDEX value
1555 * Be careful the value of the mask 0xF0000 come from d3d8types.h infos
1557 switch (stateblock->textureState[stage][WINED3DTSS_TEXCOORDINDEX] & 0xFFFF0000) {
1558 case WINED3DTSS_TCI_PASSTHRU:
1559 /*Use the specified texture coordinates contained within the vertex format. This value resolves to zero.*/
1560 glDisable(GL_TEXTURE_GEN_S);
1561 glDisable(GL_TEXTURE_GEN_T);
1562 glDisable(GL_TEXTURE_GEN_R);
1563 glDisable(GL_TEXTURE_GEN_Q);
1564 checkGLcall("glDisable(GL_TEXTURE_GEN_S,T,R,Q)");
1567 case WINED3DTSS_TCI_CAMERASPACEPOSITION:
1568 /* CameraSpacePosition means use the vertex position, transformed to camera space,
1569 * as the input texture coordinates for this stage's texture transformation. This
1570 * equates roughly to EYE_LINEAR
1573 float s_plane[] = { 1.0, 0.0, 0.0, 0.0 };
1574 float t_plane[] = { 0.0, 1.0, 0.0, 0.0 };
1575 float r_plane[] = { 0.0, 0.0, 1.0, 0.0 };
1576 float q_plane[] = { 0.0, 0.0, 0.0, 1.0 };
1577 TRACE("WINED3DTSS_TCI_CAMERASPACEPOSITION - Set eye plane\n");
1579 glMatrixMode(GL_MODELVIEW);
1582 glTexGenfv(GL_S, GL_EYE_PLANE, s_plane);
1583 glTexGenfv(GL_T, GL_EYE_PLANE, t_plane);
1584 glTexGenfv(GL_R, GL_EYE_PLANE, r_plane);
1585 glTexGenfv(GL_Q, GL_EYE_PLANE, q_plane);
1588 TRACE("WINED3DTSS_TCI_CAMERASPACEPOSITION - Set GL_TEXTURE_GEN_x and GL_x, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR\n");
1589 glEnable(GL_TEXTURE_GEN_S);
1590 checkGLcall("glEnable(GL_TEXTURE_GEN_S);");
1591 glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR);
1592 checkGLcall("glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR)");
1593 glEnable(GL_TEXTURE_GEN_T);
1594 checkGLcall("glEnable(GL_TEXTURE_GEN_T);");
1595 glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR);
1596 checkGLcall("glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR)");
1597 glEnable(GL_TEXTURE_GEN_R);
1598 checkGLcall("glEnable(GL_TEXTURE_GEN_R);");
1599 glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR);
1600 checkGLcall("glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR)");
1604 case WINED3DTSS_TCI_CAMERASPACENORMAL:
1606 if (GL_SUPPORT(NV_TEXGEN_REFLECTION)) {
1607 float s_plane[] = { 1.0, 0.0, 0.0, 0.0 };
1608 float t_plane[] = { 0.0, 1.0, 0.0, 0.0 };
1609 float r_plane[] = { 0.0, 0.0, 1.0, 0.0 };
1610 float q_plane[] = { 0.0, 0.0, 0.0, 1.0 };
1611 TRACE("WINED3DTSS_TCI_CAMERASPACENORMAL - Set eye plane\n");
1613 glMatrixMode(GL_MODELVIEW);
1616 glTexGenfv(GL_S, GL_EYE_PLANE, s_plane);
1617 glTexGenfv(GL_T, GL_EYE_PLANE, t_plane);
1618 glTexGenfv(GL_R, GL_EYE_PLANE, r_plane);
1619 glTexGenfv(GL_Q, GL_EYE_PLANE, q_plane);
1622 glEnable(GL_TEXTURE_GEN_S);
1623 checkGLcall("glEnable(GL_TEXTURE_GEN_S);");
1624 glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
1625 checkGLcall("glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV)");
1626 glEnable(GL_TEXTURE_GEN_T);
1627 checkGLcall("glEnable(GL_TEXTURE_GEN_T);");
1628 glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
1629 checkGLcall("glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV)");
1630 glEnable(GL_TEXTURE_GEN_R);
1631 checkGLcall("glEnable(GL_TEXTURE_GEN_R);");
1632 glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
1633 checkGLcall("glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV)");
1638 case WINED3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR:
1640 if (GL_SUPPORT(NV_TEXGEN_REFLECTION)) {
1641 float s_plane[] = { 1.0, 0.0, 0.0, 0.0 };
1642 float t_plane[] = { 0.0, 1.0, 0.0, 0.0 };
1643 float r_plane[] = { 0.0, 0.0, 1.0, 0.0 };
1644 float q_plane[] = { 0.0, 0.0, 0.0, 1.0 };
1645 TRACE("WINED3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR - Set eye plane\n");
1647 glMatrixMode(GL_MODELVIEW);
1650 glTexGenfv(GL_S, GL_EYE_PLANE, s_plane);
1651 glTexGenfv(GL_T, GL_EYE_PLANE, t_plane);
1652 glTexGenfv(GL_R, GL_EYE_PLANE, r_plane);
1653 glTexGenfv(GL_Q, GL_EYE_PLANE, q_plane);
1656 glEnable(GL_TEXTURE_GEN_S);
1657 checkGLcall("glEnable(GL_TEXTURE_GEN_S);");
1658 glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV);
1659 checkGLcall("glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV)");
1660 glEnable(GL_TEXTURE_GEN_T);
1661 checkGLcall("glEnable(GL_TEXTURE_GEN_T);");
1662 glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV);
1663 checkGLcall("glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV)");
1664 glEnable(GL_TEXTURE_GEN_R);
1665 checkGLcall("glEnable(GL_TEXTURE_GEN_R);");
1666 glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV);
1667 checkGLcall("glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV)");
1672 /* Unhandled types: */
1675 /* ? disable GL_TEXTURE_GEN_n ? */
1676 glDisable(GL_TEXTURE_GEN_S);
1677 glDisable(GL_TEXTURE_GEN_T);
1678 glDisable(GL_TEXTURE_GEN_R);
1679 glDisable(GL_TEXTURE_GEN_Q);
1680 FIXME("Unhandled WINED3DTSS_TEXCOORDINDEX %x\n", stateblock->textureState[stage][WINED3DTSS_TEXCOORDINDEX]);
1684 /* Update the texture matrix */
1685 if(!isStateDirty(stateblock->wineD3DDevice, STATE_TRANSFORM(WINED3DTS_TEXTURE0 + stage))) {
1686 transform_texture(STATE_TRANSFORM(WINED3DTS_TEXTURE0 + stage), stateblock);
1689 if(!isStateDirty(stateblock->wineD3DDevice, STATE_VDECL) && stateblock->wineD3DDevice->namedArraysLoaded) {
1690 /* Reload the arrays if we are using fixed function arrays to reflect the selected coord input
1691 * source. Call loadVertexData directly because there is no need to reparse the vertex declaration
1692 * and do all the things linked to it
1693 * TODO: Tidy that up to reload only the arrays of the changed unit
1695 loadVertexData(stateblock, &stateblock->wineD3DDevice->strided_streams);
1699 static void tex_bumpenvlscale(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1700 DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / WINED3D_HIGHEST_TEXTURE_STATE;
1706 tmpvalue.d = stateblock->textureState[stage][WINED3DTSS_BUMPENVLSCALE];
1707 if(tmpvalue.f != 0.0) {
1708 ERR("WINED3DTSS_BUMPENVLSCALE not supported yet\n");
1712 static void tex_bumpenvloffset(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1713 DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / WINED3D_HIGHEST_TEXTURE_STATE;
1719 tmpvalue.d = stateblock->textureState[stage][WINED3DTSS_BUMPENVLOFFSET];
1720 if(tmpvalue.f != 0.0) {
1721 ERR("WINED3DTSS_BUMPENVLOFFSET not supported yet\n");
1725 static void tex_resultarg(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1726 DWORD stage = (state - STATE_TEXTURESTAGE(0, 0)) / WINED3D_HIGHEST_TEXTURE_STATE;
1728 if(stage >= GL_LIMITS(texture_stages)) {
1732 if(stateblock->textureState[stage][WINED3DTSS_RESULTARG] != D3DTA_CURRENT) {
1733 ERR("WINED3DTSS_RESULTARG not supported yet\n");
1737 static void sampler(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1738 DWORD sampler = state - STATE_SAMPLER(0);
1739 DWORD mapped_stage = stateblock->wineD3DDevice->texUnitMap[sampler];
1745 TRACE("Sampler: %d\n", sampler);
1746 /* Enabling and disabling texture dimensions is done by texture stage state / pixel shader setup, this function
1747 * only has to bind textures and set the per texture states
1750 if (mapped_stage == -1) {
1751 TRACE("No sampler mapped to stage %d. Returning.\n", sampler);
1755 if (GL_SUPPORT(ARB_MULTITEXTURE)) {
1756 if(sampler >= GL_LIMITS(sampler_stages)) {
1759 GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
1760 checkGLcall("glActiveTextureARB");
1761 } else if (sampler > 0) {
1762 /* We can't do anything here */
1763 WARN("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
1767 if(stateblock->textures[sampler]) {
1768 BOOL texIsPow2 = FALSE;
1770 /* The fixed function np2 texture emulation uses the texture matrix to fix up the coordinates
1771 * IWineD3DBaseTexture::ApplyStateChanges multiplies the set matrix with a fixup matrix. Before the
1772 * scaling is reapplied or removed, the texture matrix has to be reapplied
1774 if(wined3d_settings.nonpower2_mode != NP2_NATIVE && sampler < MAX_TEXTURES) {
1775 if(stateblock->textureDimensions[sampler] == GL_TEXTURE_2D) {
1776 if(((IWineD3DTextureImpl *) stateblock->textures[sampler])->pow2scalingFactorX != 1.0 ||
1777 ((IWineD3DTextureImpl *) stateblock->textures[sampler])->pow2scalingFactorY != 1.0 ) {
1780 } else if(stateblock->textureDimensions[sampler] == GL_TEXTURE_CUBE_MAP_ARB) {
1781 if(((IWineD3DCubeTextureImpl *) stateblock->textures[sampler])->pow2scalingFactor != 1.0) {
1786 if(texIsPow2 || stateblock->wineD3DDevice->lastWasPow2Texture[sampler]) {
1787 transform_texture(STATE_TRANSFORM(WINED3DTS_TEXTURE0 + stateblock->wineD3DDevice->texUnitMap[sampler]), stateblock);
1788 stateblock->wineD3DDevice->lastWasPow2Texture[sampler] = texIsPow2;
1792 IWineD3DBaseTexture_PreLoad((IWineD3DBaseTexture *) stateblock->textures[sampler]);
1793 IWineD3DBaseTexture_ApplyStateChanges(stateblock->textures[sampler], stateblock->textureState[sampler], stateblock->samplerState[sampler]);
1795 if (GL_SUPPORT(EXT_TEXTURE_LOD_BIAS)) {
1796 tmpvalue.d = stateblock->samplerState[sampler][WINED3DSAMP_MIPMAPLODBIAS];
1797 glTexEnvf(GL_TEXTURE_FILTER_CONTROL_EXT,
1798 GL_TEXTURE_LOD_BIAS_EXT,
1800 checkGLcall("glTexEnvi GL_TEXTURE_LOD_BIAS_EXT ...");
1803 if (stateblock->wineD3DDevice->ps_selected_mode != SHADER_NONE && stateblock->pixelShader &&
1804 ((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.function) {
1805 /* Using a pixel shader? Verify the sampler types */
1807 /* Make sure that the texture dimensions are enabled. I don't have to disable the other
1808 * dimensions because the shader knows from which texture type to sample from. For the sake of
1809 * debugging all dimensions could be enabled and a texture with some ugly pink bound to the unused
1810 * dimensions. This should make wrong sampling sources visible :-)
1812 glEnable(stateblock->textureDimensions[sampler]);
1813 checkGLcall("glEnable(stateblock->textureDimensions[sampler])");
1814 } else if(sampler < stateblock->lowest_disabled_stage) {
1815 activate_dimensions(sampler, stateblock);
1817 if(stateblock->renderState[WINED3DRS_COLORKEYENABLE] && sampler == 0) {
1818 /* If color keying is enabled update the alpha test, it depends on the existence
1819 * of a color key in stage 0
1821 state_alpha(WINED3DRS_COLORKEYENABLE, stateblock);
1824 } else if(sampler < GL_LIMITS(texture_stages)) {
1825 if(sampler < stateblock->lowest_disabled_stage) {
1826 /* TODO: Check if the colorop is dirty to do that job
1827 * TODO: What should I do with pixel shaders here ???
1829 activate_dimensions(sampler, stateblock);
1830 } /* Otherwise tex_colorop disables the stage */
1831 glBindTexture(GL_TEXTURE_1D, stateblock->wineD3DDevice->dummyTextureName[sampler]);
1832 checkGLcall("glBindTexture(GL_TEXTURE_1D, stateblock->wineD3DDevice->dummyTextureName[sampler])");
1836 static void shaderconstant(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1837 IWineD3DDeviceImpl *device = stateblock->wineD3DDevice;
1839 /* Vertex and pixel shader states will call a shader upload, don't do anything as long one of them
1840 * has an update pending
1842 if(isStateDirty(device, STATE_VDECL) ||
1843 isStateDirty(device, STATE_PIXELSHADER)) {
1847 device->shader_backend->shader_load_constants((IWineD3DDevice *) device,
1848 stateblock->pixelShader && ((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.function,
1849 stateblock->vertexShader && ((IWineD3DVertexShaderImpl *)stateblock->vertexShader)->baseShader.function);
1852 static void pixelshader(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1855 if(stateblock->pixelShader && ((IWineD3DPixelShaderImpl *) stateblock->pixelShader)->baseShader.function != NULL) {
1856 if(!stateblock->wineD3DDevice->last_was_pshader) {
1857 /* Former draw without a pixel shader, some samplers
1858 * may be disabled because of WINED3DTSS_COLOROP = WINED3DTOP_DISABLE
1859 * make sure to enable them
1861 for(i=0; i < MAX_SAMPLERS; i++) {
1862 if(!isStateDirty(stateblock->wineD3DDevice, STATE_SAMPLER(i))) {
1863 sampler(STATE_SAMPLER(i), stateblock);
1867 /* Otherwise all samplers were activated by the code above in earlier draws, or by sampler()
1868 * if a different texture was bound. I don't have to do anything.
1872 /* Compile and bind the shader */
1873 IWineD3DPixelShader_CompileShader(stateblock->pixelShader);
1875 if(!isStateDirty(stateblock->wineD3DDevice, StateTable[STATE_VSHADER].representative)) {
1876 stateblock->wineD3DDevice->shader_backend->shader_select(
1877 (IWineD3DDevice *) stateblock->wineD3DDevice,
1879 !stateblock->vertexShader ? FALSE : ((IWineD3DVertexShaderImpl *) stateblock->vertexShader)->baseShader.function != NULL);
1881 if(!isStateDirty(stateblock->wineD3DDevice, STATE_VERTEXSHADERCONSTANT)) {
1882 shaderconstant(STATE_VERTEXSHADERCONSTANT, stateblock);
1885 stateblock->wineD3DDevice->last_was_pshader = TRUE;
1887 /* Disabled the pixel shader - color ops weren't applied
1888 * while it was enabled, so re-apply them.
1890 for(i=0; i < MAX_TEXTURES; i++) {
1891 if(!isStateDirty(stateblock->wineD3DDevice, STATE_TEXTURESTAGE(i, WINED3DTSS_COLOROP))) {
1892 tex_colorop(STATE_TEXTURESTAGE(i, WINED3DTSS_COLOROP), stateblock);
1895 stateblock->wineD3DDevice->last_was_pshader = FALSE;
1897 if(!isStateDirty(stateblock->wineD3DDevice, StateTable[STATE_VSHADER].representative)) {
1898 stateblock->wineD3DDevice->shader_backend->shader_select(
1899 (IWineD3DDevice *) stateblock->wineD3DDevice,
1901 !stateblock->vertexShader ? FALSE : ((IWineD3DVertexShaderImpl *) stateblock->vertexShader)->baseShader.function != NULL);
1903 if(!isStateDirty(stateblock->wineD3DDevice, STATE_VERTEXSHADERCONSTANT)) {
1904 shaderconstant(STATE_VERTEXSHADERCONSTANT, stateblock);
1910 static void transform_world(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1911 /* This function is called by transform_view below if the view matrix was changed too
1913 * Deliberately no check if the vertex declaration is dirty because the vdecl state
1914 * does not always update the world matrix, only on a switch between transformed
1915 * and untrannsformed draws. It *may* happen that the world matrix is set 2 times during one
1916 * draw, but that should be rather rare and cheaper in total.
1918 glMatrixMode(GL_MODELVIEW);
1919 checkGLcall("glMatrixMode");
1921 if(stateblock->wineD3DDevice->last_was_rhw) {
1923 checkGLcall("glLoadIdentity()");
1925 /* In the general case, the view matrix is the identity matrix */
1926 if (stateblock->wineD3DDevice->view_ident) {
1927 glLoadMatrixf((float *) &stateblock->transforms[WINED3DTS_WORLDMATRIX(0)].u.m[0][0]);
1928 checkGLcall("glLoadMatrixf");
1930 glLoadMatrixf((float *) &stateblock->transforms[WINED3DTS_VIEW].u.m[0][0]);
1931 checkGLcall("glLoadMatrixf");
1932 glMultMatrixf((float *) &stateblock->transforms[WINED3DTS_WORLDMATRIX(0)].u.m[0][0]);
1933 checkGLcall("glMultMatrixf");
1938 static void transform_view(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1941 /* If we are changing the View matrix, reset the light and clipping planes to the new view
1942 * NOTE: We have to reset the positions even if the light/plane is not currently
1943 * enabled, since the call to enable it will not reset the position.
1944 * NOTE2: Apparently texture transforms do NOT need reapplying
1947 PLIGHTINFOEL *lightChain = NULL;
1949 glMatrixMode(GL_MODELVIEW);
1950 checkGLcall("glMatrixMode(GL_MODELVIEW)");
1951 glLoadMatrixf((float *)(float *) &stateblock->transforms[WINED3DTS_VIEW].u.m[0][0]);
1952 checkGLcall("glLoadMatrixf(...)");
1954 /* Reset lights. TODO: Call light apply func */
1955 lightChain = stateblock->lights;
1956 while (lightChain && lightChain->glIndex != -1) {
1957 glLightfv(GL_LIGHT0 + lightChain->glIndex, GL_POSITION, lightChain->lightPosn);
1958 checkGLcall("glLightfv posn");
1959 glLightfv(GL_LIGHT0 + lightChain->glIndex, GL_SPOT_DIRECTION, lightChain->lightDirn);
1960 checkGLcall("glLightfv dirn");
1961 lightChain = lightChain->next;
1964 /* Reset Clipping Planes if clipping is enabled. TODO: Call clipplane apply func */
1965 for (k = 0; k < GL_LIMITS(clipplanes); k++) {
1966 glClipPlane(GL_CLIP_PLANE0 + k, stateblock->clipplane[k]);
1967 checkGLcall("glClipPlane");
1970 if(stateblock->wineD3DDevice->last_was_rhw) {
1972 checkGLcall("glLoadIdentity()");
1973 /* No need to update the world matrix, the identity is fine */
1977 /* Call the world matrix state, this will apply the combined WORLD + VIEW matrix
1978 * No need to do it here if the state is scheduled for update.
1980 if(!isStateDirty(stateblock->wineD3DDevice, STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(0)))) {
1981 transform_world(STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(0)), stateblock);
1985 static void transform_worldex(DWORD state, IWineD3DStateBlockImpl *stateBlock) {
1986 WARN("World matrix 1 - 255 not supported yet\n");
1989 static const GLfloat invymat[16] = {
1990 1.0f, 0.0f, 0.0f, 0.0f,
1991 0.0f, -1.0f, 0.0f, 0.0f,
1992 0.0f, 0.0f, 1.0f, 0.0f,
1993 0.0f, 0.0f, 0.0f, 1.0f};
1995 static void transform_projection(DWORD state, IWineD3DStateBlockImpl *stateblock) {
1996 glMatrixMode(GL_PROJECTION);
1997 checkGLcall("glMatrixMode(GL_PROJECTION)");
1999 checkGLcall("glLoadIdentity");
2001 if(stateblock->wineD3DDevice->last_was_rhw) {
2002 double X, Y, height, width, minZ, maxZ;
2004 X = stateblock->viewport.X;
2005 Y = stateblock->viewport.Y;
2006 height = stateblock->viewport.Height;
2007 width = stateblock->viewport.Width;
2008 minZ = stateblock->viewport.MinZ;
2009 maxZ = stateblock->viewport.MaxZ;
2011 if(!stateblock->wineD3DDevice->untransformed) {
2012 /* Transformed vertices are supposed to bypass the whole transform pipeline including
2013 * frustum clipping. This can't be done in opengl, so this code adjusts the Z range to
2014 * suppress depth clipping. This can be done because it is an orthogonal projection and
2015 * the Z coordinate does not affect the size of the primitives
2017 TRACE("Calling glOrtho with %f, %f, %f, %f\n", width, height, -minZ, -maxZ);
2018 glOrtho(X, X + width, Y + height, Y, -minZ, -maxZ);
2020 /* If the app mixes transformed and untransformed primitives we can't use the coordinate system
2021 * trick above because this would mess up transformed and untransformed Z order. Pass the z position
2022 * unmodified to opengl.
2024 * If the app depends on mixed types and disabled clipping we're out of luck without a pipeline
2025 * replacement shader.
2027 TRACE("Calling glOrtho with %f, %f, %f, %f\n", width, height, 1.0, -1.0);
2028 glOrtho(X, X + width, Y + height, Y, 1.0, -1.0);
2030 checkGLcall("glOrtho");
2032 /* Window Coord 0 is the middle of the first pixel, so translate by 3/8 pixels */
2033 glTranslatef(0.375, 0.375, 0);
2034 checkGLcall("glTranslatef(0.375, 0.375, 0)");
2035 /* D3D texture coordinates are flipped compared to OpenGL ones, so
2036 * render everything upside down when rendering offscreen. */
2037 if (stateblock->wineD3DDevice->render_offscreen) {
2038 glMultMatrixf(invymat);
2039 checkGLcall("glMultMatrixf(invymat)");
2042 /* The rule is that the window coordinate 0 does not correspond to the
2043 beginning of the first pixel, but the center of the first pixel.
2044 As a consequence if you want to correctly draw one line exactly from
2045 the left to the right end of the viewport (with all matrices set to
2046 be identity), the x coords of both ends of the line would be not
2047 -1 and 1 respectively but (-1-1/viewport_widh) and (1-1/viewport_width)
2049 glTranslatef(0.9 / stateblock->viewport.Width, -0.9 / stateblock->viewport.Height, 0);
2050 checkGLcall("glTranslatef (0.9 / width, -0.9 / height, 0)");
2052 /* D3D texture coordinates are flipped compared to OpenGL ones, so
2053 * render everything upside down when rendering offscreen. */
2054 if (stateblock->wineD3DDevice->render_offscreen) {
2055 glMultMatrixf(invymat);
2056 checkGLcall("glMultMatrixf(invymat)");
2058 glMultMatrixf((float *) &stateblock->transforms[WINED3DTS_PROJECTION].u.m[0][0]);
2059 checkGLcall("glLoadMatrixf");
2063 /* This should match any arrays loaded in loadVertexData.
2064 * stateblock impl is required for GL_SUPPORT
2065 * TODO: Only load / unload arrays if we have to.
2067 static inline void unloadVertexData(IWineD3DStateBlockImpl *stateblock) {
2070 glDisableClientState(GL_VERTEX_ARRAY);
2071 glDisableClientState(GL_NORMAL_ARRAY);
2072 glDisableClientState(GL_COLOR_ARRAY);
2073 if (GL_SUPPORT(EXT_SECONDARY_COLOR)) {
2074 glDisableClientState(GL_SECONDARY_COLOR_ARRAY_EXT);
2076 for (texture_idx = 0; texture_idx < GL_LIMITS(textures); ++texture_idx) {
2077 GL_EXTCALL(glClientActiveTextureARB(GL_TEXTURE0_ARB + texture_idx));
2078 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
2082 /* This should match any arrays loaded in loadNumberedArrays
2083 * TODO: Only load / unload arrays if we have to.
2085 static inline void unloadNumberedArrays(IWineD3DStateBlockImpl *stateblock) {
2086 /* disable any attribs (this is the same for both GLSL and ARB modes) */
2090 /* Leave all the attribs disabled */
2091 glGetIntegerv(GL_MAX_VERTEX_ATTRIBS_ARB, &maxAttribs);
2092 /* MESA does not support it right not */
2093 if (glGetError() != GL_NO_ERROR)
2095 for (i = 0; i < maxAttribs; ++i) {
2096 GL_EXTCALL(glDisableVertexAttribArrayARB(i));
2097 checkGLcall("glDisableVertexAttribArrayARB(reg);");
2101 static inline void loadNumberedArrays(IWineD3DStateBlockImpl *stateblock, WineDirect3DVertexStridedData *strided) {
2102 GLint curVBO = GL_SUPPORT(ARB_VERTEX_BUFFER_OBJECT) ? -1 : 0;
2105 for (i = 0; i < MAX_ATTRIBS; i++) {
2107 if (!strided->u.input[i].lpData && !strided->u.input[i].VBO)
2110 TRACE_(d3d_shader)("Loading array %u [VBO=%u]\n", i, strided->u.input[i].VBO);
2112 if(curVBO != strided->u.input[i].VBO) {
2113 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, strided->u.input[i].VBO));
2114 checkGLcall("glBindBufferARB");
2115 curVBO = strided->u.input[i].VBO;
2117 GL_EXTCALL(glVertexAttribPointerARB(i,
2118 WINED3D_ATR_SIZE(strided->u.input[i].dwType),
2119 WINED3D_ATR_GLTYPE(strided->u.input[i].dwType),
2120 WINED3D_ATR_NORMALIZED(strided->u.input[i].dwType),
2121 strided->u.input[i].dwStride,
2122 strided->u.input[i].lpData + stateblock->loadBaseVertexIndex * strided->u.input[i].dwStride));
2123 GL_EXTCALL(glEnableVertexAttribArrayARB(i));
2127 /* Used from 2 different functions, and too big to justify making it inlined */
2128 static void loadVertexData(IWineD3DStateBlockImpl *stateblock, WineDirect3DVertexStridedData *sd) {
2129 unsigned int textureNo = 0;
2130 unsigned int texture_idx = 0;
2131 GLint curVBO = GL_SUPPORT(ARB_VERTEX_BUFFER_OBJECT) ? -1 : 0;
2133 TRACE("Using fast vertex array code\n");
2134 /* Blend Data ---------------------------------------------- */
2135 if( (sd->u.s.blendWeights.lpData) || (sd->u.s.blendWeights.VBO) ||
2136 (sd->u.s.blendMatrixIndices.lpData) || (sd->u.s.blendMatrixIndices.VBO) ) {
2139 if (GL_SUPPORT(ARB_VERTEX_BLEND)) {
2142 glEnableClientState(GL_WEIGHT_ARRAY_ARB);
2143 checkGLcall("glEnableClientState(GL_WEIGHT_ARRAY_ARB)");
2146 TRACE("Blend %d %p %d\n", WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType),
2147 sd->u.s.blendWeights.lpData + stateblock->loadBaseVertexIndex * sd->u.s.blendWeights.dwStride, sd->u.s.blendWeights.dwStride);
2148 /* FIXME("TODO\n");*/
2149 /* Note dwType == float3 or float4 == 2 or 3 */
2152 /* with this on, the normals appear to be being modified,
2153 but the vertices aren't being translated as they should be
2154 Maybe the world matrix aren't being setup properly? */
2155 glVertexBlendARB(WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType) + 1);
2159 VTRACE(("glWeightPointerARB(%d, GL_FLOAT, %d, %p)\n",
2160 WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType) ,
2161 sd->u.s.blendWeights.dwStride,
2162 sd->u.s.blendWeights.lpData + stateblock->loadBaseVertexIndex * sd->u.s.blendWeights.dwStride));
2164 if(curVBO != sd->u.s.blendWeights.VBO) {
2165 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, sd->u.s.blendWeights.VBO));
2166 checkGLcall("glBindBufferARB");
2167 curVBO = sd->u.s.blendWeights.VBO;
2170 GL_EXTCALL(glWeightPointerARB)(
2171 WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType),
2172 WINED3D_ATR_GLTYPE(sd->u.s.blendWeights.dwType),
2173 sd->u.s.blendWeights.dwStride,
2174 sd->u.s.blendWeights.lpData + stateblock->loadBaseVertexIndex * sd->u.s.blendWeights.dwStride);
2176 checkGLcall("glWeightPointerARB");
2178 if((sd->u.s.blendMatrixIndices.lpData) || (sd->u.s.blendMatrixIndices.VBO)){
2179 static BOOL showfixme = TRUE;
2181 FIXME("blendMatrixIndices support\n");
2186 } else if (GL_SUPPORT(EXT_VERTEX_WEIGHTING)) {
2187 /* FIXME("TODO\n");*/
2190 GL_EXTCALL(glVertexWeightPointerEXT)(
2191 WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType),
2192 WINED3D_ATR_GLTYPE(sd->u.s.blendWeights.dwType),
2193 sd->u.s.blendWeights.dwStride,
2194 sd->u.s.blendWeights.lpData + stateblock->loadBaseVertexIndex * sd->u.s.blendWeights.dwStride);
2195 checkGLcall("glVertexWeightPointerEXT(numBlends, ...)");
2196 glEnableClientState(GL_VERTEX_WEIGHT_ARRAY_EXT);
2197 checkGLcall("glEnableClientState(GL_VERTEX_WEIGHT_ARRAY_EXT)");
2201 /* TODO: support blends in fixupVertices */
2202 FIXME("unsupported blending in openGl\n");
2205 if (GL_SUPPORT(ARB_VERTEX_BLEND)) {
2206 #if 0 /* TODO: Vertex blending */
2207 glDisable(GL_VERTEX_BLEND_ARB);
2209 TRACE("ARB_VERTEX_BLEND\n");
2210 } else if (GL_SUPPORT(EXT_VERTEX_WEIGHTING)) {
2211 TRACE(" EXT_VERTEX_WEIGHTING\n");
2212 glDisableClientState(GL_VERTEX_WEIGHT_ARRAY_EXT);
2213 checkGLcall("glDisableClientState(GL_VERTEX_WEIGHT_ARRAY_EXT)");
2218 #if 0 /* FOG ----------------------------------------------*/
2219 if (sd->u.s.fog.lpData || sd->u.s.fog.VBO) {
2221 if (GL_SUPPORT(EXT_FOG_COORD) {
2222 glEnableClientState(GL_FOG_COORDINATE_EXT);
2223 (GL_EXTCALL)(FogCoordPointerEXT)(
2224 WINED3D_ATR_GLTYPE(sd->u.s.fog.dwType),
2225 sd->u.s.fog.dwStride,
2226 sd->u.s.fog.lpData + stateblock->loadBaseVertexIndex * sd->u.s.fog.dwStride);
2228 /* don't bother falling back to 'slow' as we don't support software FOG yet. */
2229 /* FIXME: fixme once */
2230 TRACE("Hardware support for FOG is not avaiable, FOG disabled.\n");
2233 if (GL_SUPPRT(EXT_FOR_COORD) {
2234 /* make sure fog is disabled */
2235 glDisableClientState(GL_FOG_COORDINATE_EXT);
2240 #if 0 /* tangents ----------------------------------------------*/
2241 if (sd->u.s.tangent.lpData || sd->u.s.tangent.VBO ||
2242 sd->u.s.binormal.lpData || sd->u.s.binormal.VBO) {
2244 if (GL_SUPPORT(EXT_COORDINATE_FRAME) {
2245 if (sd->u.s.tangent.lpData || sd->u.s.tangent.VBO) {
2246 glEnable(GL_TANGENT_ARRAY_EXT);
2247 (GL_EXTCALL)(TangentPointerEXT)(
2248 WINED3D_ATR_GLTYPE(sd->u.s.tangent.dwType),
2249 sd->u.s.tangent.dwStride,
2250 sd->u.s.tangent.lpData + stateblock->loadBaseVertexIndex * sd->u.s.tangent.dwStride);
2252 glDisable(GL_TANGENT_ARRAY_EXT);
2254 if (sd->u.s.binormal.lpData || sd->u.s.binormal.VBO) {
2255 glEnable(GL_BINORMAL_ARRAY_EXT);
2256 (GL_EXTCALL)(BinormalPointerEXT)(
2257 WINED3D_ATR_GLTYPE(sd->u.s.binormal.dwType),
2258 sd->u.s.binormal.dwStride,
2259 sd->u.s.binormal.lpData + stateblock->loadBaseVertexIndex * sd->u.s.binormal.dwStride);
2261 glDisable(GL_BINORMAL_ARRAY_EXT);
2265 /* don't bother falling back to 'slow' as we don't support software tangents and binormals yet . */
2266 /* FIXME: fixme once */
2267 TRACE("Hardware support for tangents and binormals is not avaiable, tangents and binormals disabled.\n");
2270 if (GL_SUPPORT(EXT_COORDINATE_FRAME) {
2271 /* make sure fog is disabled */
2272 glDisable(GL_TANGENT_ARRAY_EXT);
2273 glDisable(GL_BINORMAL_ARRAY_EXT);
2278 /* Point Size ----------------------------------------------*/
2279 if (sd->u.s.pSize.lpData || sd->u.s.pSize.VBO) {
2281 /* no such functionality in the fixed function GL pipeline */
2282 TRACE("Cannot change ptSize here in openGl\n");
2283 /* TODO: Implement this function in using shaders if they are available */
2287 /* Vertex Pointers -----------------------------------------*/
2288 if (sd->u.s.position.lpData != NULL || sd->u.s.position.VBO != 0) {
2289 /* Note dwType == float3 or float4 == 2 or 3 */
2290 VTRACE(("glVertexPointer(%d, GL_FLOAT, %d, %p)\n",
2291 sd->u.s.position.dwStride,
2292 sd->u.s.position.dwType + 1,
2293 sd->u.s.position.lpData));
2295 if(curVBO != sd->u.s.position.VBO) {
2296 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, sd->u.s.position.VBO));
2297 checkGLcall("glBindBufferARB");
2298 curVBO = sd->u.s.position.VBO;
2301 /* min(WINED3D_ATR_SIZE(position),3) to Disable RHW mode as 'w' coord
2302 handling for rhw mode should not impact screen position whereas in GL it does.
2303 This may result in very slightly distored textures in rhw mode, but
2304 a very minimal different. There's always the other option of
2305 fixing the view matrix to prevent w from having any effect
2307 This only applies to user pointer sources, in VBOs the vertices are fixed up
2309 if(sd->u.s.position.VBO == 0) {
2310 glVertexPointer(3 /* min(WINED3D_ATR_SIZE(sd->u.s.position.dwType),3) */,
2311 WINED3D_ATR_GLTYPE(sd->u.s.position.dwType),
2312 sd->u.s.position.dwStride, sd->u.s.position.lpData + stateblock->loadBaseVertexIndex * sd->u.s.position.dwStride);
2315 WINED3D_ATR_SIZE(sd->u.s.position.dwType),
2316 WINED3D_ATR_GLTYPE(sd->u.s.position.dwType),
2317 sd->u.s.position.dwStride, sd->u.s.position.lpData + stateblock->loadBaseVertexIndex * sd->u.s.position.dwStride);
2319 checkGLcall("glVertexPointer(...)");
2320 glEnableClientState(GL_VERTEX_ARRAY);
2321 checkGLcall("glEnableClientState(GL_VERTEX_ARRAY)");
2324 glDisableClientState(GL_VERTEX_ARRAY);
2325 checkGLcall("glDisableClientState(GL_VERTEX_ARRAY)");
2328 /* Normals -------------------------------------------------*/
2329 if (sd->u.s.normal.lpData || sd->u.s.normal.VBO) {
2330 /* Note dwType == float3 or float4 == 2 or 3 */
2331 VTRACE(("glNormalPointer(GL_FLOAT, %d, %p)\n",
2332 sd->u.s.normal.dwStride,
2333 sd->u.s.normal.lpData));
2334 if(curVBO != sd->u.s.normal.VBO) {
2335 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, sd->u.s.normal.VBO));
2336 checkGLcall("glBindBufferARB");
2337 curVBO = sd->u.s.normal.VBO;
2340 WINED3D_ATR_GLTYPE(sd->u.s.normal.dwType),
2341 sd->u.s.normal.dwStride,
2342 sd->u.s.normal.lpData + stateblock->loadBaseVertexIndex * sd->u.s.normal.dwStride);
2343 checkGLcall("glNormalPointer(...)");
2344 glEnableClientState(GL_NORMAL_ARRAY);
2345 checkGLcall("glEnableClientState(GL_NORMAL_ARRAY)");
2348 glDisableClientState(GL_NORMAL_ARRAY);
2349 checkGLcall("glDisableClientState(GL_NORMAL_ARRAY)");
2350 glNormal3f(0, 0, 1);
2351 checkGLcall("glNormal3f(0, 0, 1)");
2354 /* Diffuse Colour --------------------------------------------*/
2355 /* WARNING: Data here MUST be in RGBA format, so cannot */
2356 /* go directly into fast mode from app pgm, because */
2357 /* directx requires data in BGRA format. */
2358 /* currently fixupVertices swizels the format, but this isn't */
2359 /* very practical when using VBOS */
2360 /* NOTE: Unless we write a vertex shader to swizel the colour */
2361 /* , or the user doesn't care and wants the speed advantage */
2363 if (sd->u.s.diffuse.lpData || sd->u.s.diffuse.VBO) {
2364 /* Note dwType == float3 or float4 == 2 or 3 */
2365 VTRACE(("glColorPointer(4, GL_UNSIGNED_BYTE, %d, %p)\n",
2366 sd->u.s.diffuse.dwStride,
2367 sd->u.s.diffuse.lpData));
2369 if(curVBO != sd->u.s.diffuse.VBO) {
2370 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, sd->u.s.diffuse.VBO));
2371 checkGLcall("glBindBufferARB");
2372 curVBO = sd->u.s.diffuse.VBO;
2374 glColorPointer(4, GL_UNSIGNED_BYTE,
2375 sd->u.s.diffuse.dwStride,
2376 sd->u.s.diffuse.lpData + stateblock->loadBaseVertexIndex * sd->u.s.diffuse.dwStride);
2377 checkGLcall("glColorPointer(4, GL_UNSIGNED_BYTE, ...)");
2378 glEnableClientState(GL_COLOR_ARRAY);
2379 checkGLcall("glEnableClientState(GL_COLOR_ARRAY)");
2382 glDisableClientState(GL_COLOR_ARRAY);
2383 checkGLcall("glDisableClientState(GL_COLOR_ARRAY)");
2384 glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
2385 checkGLcall("glColor4f(1, 1, 1, 1)");
2388 /* Specular Colour ------------------------------------------*/
2389 if (sd->u.s.specular.lpData || sd->u.s.specular.VBO) {
2390 TRACE("setting specular colour\n");
2391 /* Note dwType == float3 or float4 == 2 or 3 */
2392 VTRACE(("glSecondaryColorPointer(4, GL_UNSIGNED_BYTE, %d, %p)\n",
2393 sd->u.s.specular.dwStride,
2394 sd->u.s.specular.lpData));
2395 if (GL_SUPPORT(EXT_SECONDARY_COLOR)) {
2396 if(curVBO != sd->u.s.specular.VBO) {
2397 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, sd->u.s.specular.VBO));
2398 checkGLcall("glBindBufferARB");
2399 curVBO = sd->u.s.specular.VBO;
2401 GL_EXTCALL(glSecondaryColorPointerEXT)(4, GL_UNSIGNED_BYTE,
2402 sd->u.s.specular.dwStride,
2403 sd->u.s.specular.lpData + stateblock->loadBaseVertexIndex * sd->u.s.specular.dwStride);
2404 vcheckGLcall("glSecondaryColorPointerEXT(4, GL_UNSIGNED_BYTE, ...)");
2405 glEnableClientState(GL_SECONDARY_COLOR_ARRAY_EXT);
2406 vcheckGLcall("glEnableClientState(GL_SECONDARY_COLOR_ARRAY_EXT)");
2409 /* Missing specular color is not critical, no warnings */
2410 VTRACE(("Specular colour is not supported in this GL implementation\n"));
2414 if (GL_SUPPORT(EXT_SECONDARY_COLOR)) {
2416 glDisableClientState(GL_SECONDARY_COLOR_ARRAY_EXT);
2417 checkGLcall("glDisableClientState(GL_SECONDARY_COLOR_ARRAY_EXT)");
2418 GL_EXTCALL(glSecondaryColor3fEXT)(0, 0, 0);
2419 checkGLcall("glSecondaryColor3fEXT(0, 0, 0)");
2422 /* Missing specular color is not critical, no warnings */
2423 VTRACE(("Specular colour is not supported in this GL implementation\n"));
2427 /* Texture coords -------------------------------------------*/
2429 for (textureNo = 0, texture_idx = 0; textureNo < GL_LIMITS(texture_stages); ++textureNo) {
2430 /* The code below uses glClientActiveTexture and glMultiTexCoord* which are all part of the GL_ARB_multitexture extension. */
2431 /* Abort if we don't support the extension. */
2432 if (!GL_SUPPORT(ARB_MULTITEXTURE)) {
2433 FIXME("Program using multiple concurrent textures which this opengl implementation doesn't support\n");
2437 if (/*!GL_SUPPORT(NV_REGISTER_COMBINERS) || stateblock->textures[textureNo]*/ TRUE) {
2438 /* Select the correct texture stage */
2439 GL_EXTCALL(glClientActiveTextureARB(GL_TEXTURE0_ARB + texture_idx));
2442 if (stateblock->textures[textureNo] != NULL) {
2443 int coordIdx = stateblock->textureState[textureNo][WINED3DTSS_TEXCOORDINDEX];
2445 if (coordIdx >= MAX_TEXTURES) {
2446 VTRACE(("tex: %d - Skip tex coords, as being system generated\n", textureNo));
2447 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
2448 GL_EXTCALL(glMultiTexCoord4fARB(GL_TEXTURE0_ARB + texture_idx, 0, 0, 0, 1));
2450 } else if (sd->u.s.texCoords[coordIdx].lpData == NULL && sd->u.s.texCoords[coordIdx].VBO == 0) {
2451 VTRACE(("Bound texture but no texture coordinates supplied, so skipping\n"));
2452 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
2453 GL_EXTCALL(glMultiTexCoord4fARB(GL_TEXTURE0_ARB + texture_idx, 0, 0, 0, 1));
2456 TRACE("Setting up texture %u, idx %d, cordindx %u, data %p\n",
2457 textureNo, texture_idx, coordIdx, sd->u.s.texCoords[coordIdx].lpData);
2458 if(curVBO != sd->u.s.texCoords[coordIdx].VBO) {
2459 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, sd->u.s.texCoords[coordIdx].VBO));
2460 checkGLcall("glBindBufferARB");
2461 curVBO = sd->u.s.texCoords[coordIdx].VBO;
2463 /* The coords to supply depend completely on the fvf / vertex shader */
2465 WINED3D_ATR_SIZE(sd->u.s.texCoords[coordIdx].dwType),
2466 WINED3D_ATR_GLTYPE(sd->u.s.texCoords[coordIdx].dwType),
2467 sd->u.s.texCoords[coordIdx].dwStride,
2468 sd->u.s.texCoords[coordIdx].lpData + stateblock->loadBaseVertexIndex * sd->u.s.texCoords[coordIdx].dwStride);
2469 glEnableClientState(GL_TEXTURE_COORD_ARRAY);
2471 } else if (!GL_SUPPORT(NV_REGISTER_COMBINERS)) {
2472 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
2473 GL_EXTCALL(glMultiTexCoord4fARB(GL_TEXTURE0_ARB + textureNo, 0, 0, 0, 1));
2475 if (/*!GL_SUPPORT(NV_REGISTER_COMBINERS) || stateblock->textures[textureNo]*/ TRUE) ++texture_idx;
2477 if (GL_SUPPORT(NV_REGISTER_COMBINERS)) {
2478 for (textureNo = texture_idx; textureNo < GL_LIMITS(textures); ++textureNo) {
2479 GL_EXTCALL(glClientActiveTextureARB(GL_TEXTURE0_ARB + textureNo));
2480 glDisableClientState(GL_TEXTURE_COORD_ARRAY);
2481 GL_EXTCALL(glMultiTexCoord4fARB(GL_TEXTURE0_ARB + textureNo, 0, 0, 0, 1));
2486 inline void drawPrimitiveTraceDataLocations(
2487 WineDirect3DVertexStridedData *dataLocations) {
2489 /* Dump out what parts we have supplied */
2490 TRACE("Strided Data:\n");
2491 TRACE_STRIDED((dataLocations), position);
2492 TRACE_STRIDED((dataLocations), blendWeights);
2493 TRACE_STRIDED((dataLocations), blendMatrixIndices);
2494 TRACE_STRIDED((dataLocations), normal);
2495 TRACE_STRIDED((dataLocations), pSize);
2496 TRACE_STRIDED((dataLocations), diffuse);
2497 TRACE_STRIDED((dataLocations), specular);
2498 TRACE_STRIDED((dataLocations), texCoords[0]);
2499 TRACE_STRIDED((dataLocations), texCoords[1]);
2500 TRACE_STRIDED((dataLocations), texCoords[2]);
2501 TRACE_STRIDED((dataLocations), texCoords[3]);
2502 TRACE_STRIDED((dataLocations), texCoords[4]);
2503 TRACE_STRIDED((dataLocations), texCoords[5]);
2504 TRACE_STRIDED((dataLocations), texCoords[6]);
2505 TRACE_STRIDED((dataLocations), texCoords[7]);
2506 TRACE_STRIDED((dataLocations), position2);
2507 TRACE_STRIDED((dataLocations), normal2);
2508 TRACE_STRIDED((dataLocations), tangent);
2509 TRACE_STRIDED((dataLocations), binormal);
2510 TRACE_STRIDED((dataLocations), tessFactor);
2511 TRACE_STRIDED((dataLocations), fog);
2512 TRACE_STRIDED((dataLocations), depth);
2513 TRACE_STRIDED((dataLocations), sample);
2518 /* Helper for vertexdeclaration() */
2519 static inline void handleStreams(IWineD3DStateBlockImpl *stateblock, BOOL useVertexShaderFunction) {
2520 IWineD3DDeviceImpl *device = stateblock->wineD3DDevice;
2522 WineDirect3DVertexStridedData *dataLocations = &device->strided_streams;
2524 if(device->up_strided) {
2525 /* Note: this is a ddraw fixed-function code path */
2526 TRACE("================ Strided Input ===================\n");
2527 memcpy(dataLocations, device->up_strided, sizeof(*dataLocations));
2530 drawPrimitiveTraceDataLocations(dataLocations);
2532 } else if (stateblock->vertexDecl || stateblock->vertexShader) {
2533 /* Note: This is a fixed function or shader codepath.
2534 * This means it must handle both types of strided data.
2535 * Shaders must go through here to zero the strided data, even if they
2536 * don't set any declaration at all
2538 TRACE("================ Vertex Declaration ===================\n");
2539 memset(dataLocations, 0, sizeof(*dataLocations));
2541 if (stateblock->vertexDecl != NULL ||
2542 ((IWineD3DVertexShaderImpl *)stateblock->vertexShader)->vertexDeclaration != NULL) {
2544 primitiveDeclarationConvertToStridedData((IWineD3DDevice *) device, useVertexShaderFunction,
2545 dataLocations, &fixup);
2548 /* Note: This codepath is not reachable from d3d9 (see fvf->decl9 conversion)
2549 * It is reachable through d3d8, but only for fixed-function.
2550 * It will not work properly for shaders.
2552 TRACE("================ FVF ===================\n");
2553 memset(dataLocations, 0, sizeof(*dataLocations));
2554 primitiveConvertToStridedData((IWineD3DDevice *) device, dataLocations,
2557 drawPrimitiveTraceDataLocations(dataLocations);
2561 /* Unload the old arrays before loading the new ones to get old junk out */
2562 if(device->numberedArraysLoaded) {
2563 unloadNumberedArrays(stateblock);
2564 device->numberedArraysLoaded = FALSE;
2566 if(device->namedArraysLoaded) {
2567 unloadVertexData(stateblock);
2568 device->namedArraysLoaded = FALSE;
2571 if(useVertexShaderFunction) {
2572 TRACE("Loading numbered arrays\n");
2573 loadNumberedArrays(stateblock, dataLocations);
2574 device->useDrawStridedSlow = FALSE;
2575 device->numberedArraysLoaded = TRUE;
2577 (dataLocations->u.s.pSize.lpData == NULL &&
2578 dataLocations->u.s.diffuse.lpData == NULL &&
2579 dataLocations->u.s.specular.lpData == NULL)) {
2580 /* Load the vertex data using named arrays */
2581 TRACE("Loading vertex data\n");
2582 loadVertexData(stateblock, dataLocations);
2583 device->useDrawStridedSlow = FALSE;
2584 device->namedArraysLoaded = TRUE;
2586 TRACE("Not loading vertex data\n");
2587 device->useDrawStridedSlow = TRUE;
2590 /* Generate some fixme's if unsupported functionality is being used */
2591 #define BUFFER_OR_DATA(_attribute) dataLocations->u.s._attribute.lpData
2592 /* TODO: Either support missing functionality in fixupVertices or by creating a shader to replace the pipeline. */
2593 if (!useVertexShaderFunction && (BUFFER_OR_DATA(blendMatrixIndices) || BUFFER_OR_DATA(blendWeights))) {
2594 FIXME("Blending data is only valid with vertex shaders %p %p\n",dataLocations->u.s.blendWeights.lpData,dataLocations->u.s.blendWeights.lpData);
2596 if (!useVertexShaderFunction && (BUFFER_OR_DATA(position2) || BUFFER_OR_DATA(normal2))) {
2597 FIXME("Tweening is only valid with vertex shaders\n");
2599 if (!useVertexShaderFunction && (BUFFER_OR_DATA(tangent) || BUFFER_OR_DATA(binormal))) {
2600 FIXME("Tangent and binormal bump mapping is only valid with vertex shaders\n");
2602 if (!useVertexShaderFunction && (BUFFER_OR_DATA(tessFactor) || BUFFER_OR_DATA(fog) || BUFFER_OR_DATA(depth) || BUFFER_OR_DATA(sample))) {
2603 FIXME("Extended attributes are only valid with vertex shaders\n");
2605 #undef BUFFER_OR_DATA
2608 static void vertexdeclaration(DWORD state, IWineD3DStateBlockImpl *stateblock) {
2609 BOOL useVertexShaderFunction = FALSE, updateFog = FALSE;
2611 /* Some stuff is in the device until we have per context tracking */
2612 IWineD3DDeviceImpl *device = stateblock->wineD3DDevice;
2613 BOOL wasrhw = device->last_was_rhw;
2615 /* Shaders can be implemented using ARB_PROGRAM, GLSL, or software -
2616 * here simply check whether a shader was set, or the user disabled shaders
2618 if (device->vs_selected_mode != SHADER_NONE && stateblock->vertexShader &&
2619 ((IWineD3DVertexShaderImpl *)stateblock->vertexShader)->baseShader.function != NULL) {
2620 useVertexShaderFunction = TRUE;
2622 if(((IWineD3DVertexShaderImpl *)stateblock->vertexShader)->usesFog != device->last_was_foggy_shader) {
2625 } else if(device->last_was_foggy_shader) {
2629 handleStreams(stateblock, useVertexShaderFunction);
2631 /* Do I have to use ? TRUE : FALSE ? Or can I rely on 15==15 beeing equal to TRUE(=1)? */
2632 transformed = ((device->strided_streams.u.s.position.lpData != NULL ||
2633 device->strided_streams.u.s.position.VBO != 0) &&
2634 device->strided_streams.u.s.position_transformed) ? TRUE : FALSE;
2636 if(transformed != device->last_was_rhw && !useVertexShaderFunction) {
2640 /* Reapply lighting if it is not sheduled for reapplication already */
2641 if(!isStateDirty(device, STATE_RENDER(WINED3DRS_LIGHTING))) {
2642 state_lighting(STATE_RENDER(WINED3DRS_LIGHTING), stateblock);
2645 if (!useVertexShaderFunction && transformed) {
2646 stateblock->wineD3DDevice->last_was_rhw = TRUE;
2649 /* Untransformed, so relies on the view and projection matrices */
2650 device->last_was_rhw = FALSE;
2651 /* This turns off the Z scale trick to 'disable' viewport frustum clipping in rhw mode*/
2652 device->untransformed = TRUE;
2654 /* Todo for sw shaders: Vertex Shader output is already transformed, so set up identity matrices
2655 * Not needed as long as only hw shaders are supported
2658 /* This sets the shader output position correction constants.
2659 * TODO: Move to the viewport state
2661 if (useVertexShaderFunction) {
2662 device->posFixup[1] = device->render_offscreen ? -1.0 : 1.0;
2666 /* Don't have to apply the matrices when vertex shaders are used. When vshaders are turned
2667 * off this function will be called again anyway to make sure they're properly set
2669 if(!useVertexShaderFunction) {
2670 /* TODO: Move this mainly to the viewport state and only apply when the vp has changed
2671 * or transformed / untransformed was switched
2673 if(wasrhw != device->last_was_rhw &&
2674 !isStateDirty(stateblock->wineD3DDevice, STATE_TRANSFORM(WINED3DTS_PROJECTION)) &&
2675 !isStateDirty(stateblock->wineD3DDevice, STATE_VIEWPORT)) {
2676 transform_projection(STATE_TRANSFORM(WINED3DTS_PROJECTION), stateblock);
2678 /* World matrix needs reapplication here only if we're switching between rhw and non-rhw
2681 * If a vertex shader is used, the world matrix changed and then vertex shader unbound
2682 * this check will fail and the matrix not applied again. This is OK because a simple
2683 * world matrix change reapplies the matrix - These checks here are only to satisfy the
2684 * needs of the vertex declaration.
2686 * World and view matrix go into the same gl matrix, so only apply them when neither is
2689 if(transformed != wasrhw &&
2690 !isStateDirty(stateblock->wineD3DDevice, STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(0))) &&
2691 !isStateDirty(stateblock->wineD3DDevice, STATE_TRANSFORM(WINED3DTS_VIEW))) {
2692 transform_world(STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(0)), stateblock);
2695 if(!isStateDirty(stateblock->wineD3DDevice, STATE_RENDER(WINED3DRS_COLORVERTEX))) {
2696 state_colormat(STATE_RENDER(WINED3DRS_COLORVERTEX), stateblock);
2699 /* We compile the shader here because we need the vertex declaration
2700 * in order to determine if we need to do any swizzling for D3DCOLOR
2701 * registers. If the shader is already compiled this call will do nothing. */
2702 IWineD3DVertexShader_CompileShader(stateblock->vertexShader);
2705 if(useVertexShaderFunction || device->last_was_vshader) {
2706 BOOL usePixelShaderFunction = device->ps_selected_mode != SHADER_NONE &&
2707 stateblock->pixelShader &&
2708 ((IWineD3DPixelShaderImpl *)stateblock->pixelShader)->baseShader.function;
2710 /* Vertex and pixel shaders are applied together for now, so let the last dirty state do the
2713 if(!isStateDirty(device, STATE_PIXELSHADER)) {
2714 device->shader_backend->shader_select((IWineD3DDevice *) device, usePixelShaderFunction, useVertexShaderFunction);
2716 if(!isStateDirty(stateblock->wineD3DDevice, STATE_VERTEXSHADERCONSTANT) && (useVertexShaderFunction || usePixelShaderFunction)) {
2717 shaderconstant(STATE_VERTEXSHADERCONSTANT, stateblock);
2720 device->last_was_vshader = useVertexShaderFunction;
2724 state_fog(STATE_RENDER(WINED3DRS_FOGENABLE), stateblock);
2728 static void viewport(DWORD state, IWineD3DStateBlockImpl *stateblock) {
2729 glDepthRange(stateblock->viewport.MinZ, stateblock->viewport.MaxZ);
2730 checkGLcall("glDepthRange");
2731 /* Note: GL requires lower left, DirectX supplies upper left */
2732 /* TODO: replace usage of renderTarget with context management */
2733 glViewport(stateblock->viewport.X,
2734 (((IWineD3DSurfaceImpl *)stateblock->wineD3DDevice->render_targets[0])->currentDesc.Height - (stateblock->viewport.Y + stateblock->viewport.Height)),
2735 stateblock->viewport.Width, stateblock->viewport.Height);
2737 checkGLcall("glViewport");
2739 stateblock->wineD3DDevice->posFixup[2] = 0.9 / stateblock->viewport.Width;
2740 stateblock->wineD3DDevice->posFixup[3] = -0.9 / stateblock->viewport.Height;
2741 if(!isStateDirty(stateblock->wineD3DDevice, STATE_TRANSFORM(D3DTS_PROJECTION))) {
2742 transform_projection(STATE_TRANSFORM(D3DTS_PROJECTION), stateblock);
2747 const struct StateEntry StateTable[] =
2749 /* State name representative, apply function */
2750 { /* 0, Undefined */ 0, state_undefined },
2751 { /* 1, WINED3DRS_TEXTUREHANDLE */ 0 /* Handled in ddraw */, state_undefined },
2752 { /* 2, WINED3DRS_ANTIALIAS */ STATE_RENDER(WINED3DRS_ANTIALIAS), state_antialias },
2753 { /* 3, WINED3DRS_TEXTUREADDRESS */ 0 /* Handled in ddraw */, state_undefined },
2754 { /* 4, WINED3DRS_TEXTUREPERSPECTIVE */ STATE_RENDER(WINED3DRS_TEXTUREPERSPECTIVE), state_perspective },
2755 { /* 5, WINED3DRS_WRAPU */ STATE_RENDER(WINED3DRS_WRAPU), state_wrapu },
2756 { /* 6, WINED3DRS_WRAPV */ STATE_RENDER(WINED3DRS_WRAPV), state_wrapv },
2757 { /* 7, WINED3DRS_ZENABLE */ STATE_RENDER(WINED3DRS_ZENABLE), state_zenable },
2758 { /* 8, WINED3DRS_FILLMODE */ STATE_RENDER(WINED3DRS_FILLMODE), state_fillmode },
2759 { /* 9, WINED3DRS_SHADEMODE */ STATE_RENDER(WINED3DRS_SHADEMODE), state_shademode },
2760 { /* 10, WINED3DRS_LINEPATTERN */ STATE_RENDER(WINED3DRS_LINEPATTERN), state_linepattern },
2761 { /* 11, WINED3DRS_MONOENABLE */ STATE_RENDER(WINED3DRS_MONOENABLE), state_monoenable },
2762 { /* 12, WINED3DRS_ROP2 */ STATE_RENDER(WINED3DRS_ROP2), state_rop2 },
2763 { /* 13, WINED3DRS_PLANEMASK */ STATE_RENDER(WINED3DRS_PLANEMASK), state_planemask },
2764 { /* 14, WINED3DRS_ZWRITEENABLE */ STATE_RENDER(WINED3DRS_ZWRITEENABLE), state_zwritenable },
2765 { /* 15, WINED3DRS_ALPHATESTENABLE */ STATE_RENDER(WINED3DRS_ALPHATESTENABLE), state_alpha },
2766 { /* 16, WINED3DRS_LASTPIXEL */ STATE_RENDER(WINED3DRS_LASTPIXEL), state_lastpixel },
2767 { /* 17, WINED3DRS_TEXTUREMAG */ 0 /* Handled in ddraw */, state_undefined },
2768 { /* 18, WINED3DRS_TEXTUREMIN */ 0 /* Handled in ddraw */, state_undefined },
2769 { /* 19, WINED3DRS_SRCBLEND */ STATE_RENDER(WINED3DRS_ALPHABLENDENABLE), state_blend },
2770 { /* 20, WINED3DRS_DESTBLEND */ STATE_RENDER(WINED3DRS_ALPHABLENDENABLE), state_blend },
2771 { /* 21, WINED3DRS_TEXTUREMAPBLEND */ 0 /* Handled in ddraw */, state_undefined },
2772 { /* 22, WINED3DRS_CULLMODE */ STATE_RENDER(WINED3DRS_CULLMODE), state_cullmode },
2773 { /* 23, WINED3DRS_ZFUNC */ STATE_RENDER(WINED3DRS_ZFUNC), state_zfunc },
2774 { /* 24, WINED3DRS_ALPHAREF */ STATE_RENDER(WINED3DRS_ALPHATESTENABLE), state_alpha },
2775 { /* 25, WINED3DRS_ALPHAFUNC */ STATE_RENDER(WINED3DRS_ALPHATESTENABLE), state_alpha },
2776 { /* 26, WINED3DRS_DITHERENABLE */ STATE_RENDER(WINED3DRS_DITHERENABLE), state_ditherenable },
2777 { /* 27, WINED3DRS_ALPHABLENDENABLE */ STATE_RENDER(WINED3DRS_ALPHABLENDENABLE), state_blend },
2778 { /* 28, WINED3DRS_FOGENABLE */ STATE_RENDER(WINED3DRS_FOGENABLE), state_fog },
2779 { /* 29, WINED3DRS_SPECULARENABLE */ STATE_RENDER(WINED3DRS_SPECULARENABLE), state_specularenable},
2780 { /* 30, WINED3DRS_ZVISIBLE */ 0 /* Not supported according to the msdn */, state_nogl },
2781 { /* 31, WINED3DRS_SUBPIXEL */ STATE_RENDER(WINED3DRS_SUBPIXEL), state_subpixel },
2782 { /* 32, WINED3DRS_SUBPIXELX */ STATE_RENDER(WINED3DRS_SUBPIXELX), state_subpixelx },
2783 { /* 33, WINED3DRS_STIPPLEDALPHA */ STATE_RENDER(WINED3DRS_STIPPLEDALPHA), state_stippledalpha },
2784 { /* 34, WINED3DRS_FOGCOLOR */ STATE_RENDER(WINED3DRS_FOGCOLOR), state_fogcolor },
2785 { /* 35, WINED3DRS_FOGTABLEMODE */ STATE_RENDER(WINED3DRS_FOGENABLE), state_fog },
2786 { /* 36, WINED3DRS_FOGSTART */ STATE_RENDER(WINED3DRS_FOGENABLE), state_fog },
2787 { /* 37, WINED3DRS_FOGEND */ STATE_RENDER(WINED3DRS_FOGENABLE), state_fog },
2788 { /* 38, WINED3DRS_FOGDENSITY */ STATE_RENDER(WINED3DRS_FOGDENSITY), state_fogdensity },
2789 { /* 39, WINED3DRS_STIPPLEENABLE */ STATE_RENDER(WINED3DRS_STIPPLEENABLE), state_stippleenable },
2790 { /* 40, WINED3DRS_EDGEANTIALIAS */ STATE_RENDER(WINED3DRS_ALPHABLENDENABLE), state_blend },
2791 { /* 41, WINED3DRS_COLORKEYENABLE */ STATE_RENDER(WINED3DRS_ALPHATESTENABLE), state_alpha },
2792 { /* 42, undefined */ 0, state_undefined },
2793 { /* 43, WINED3DRS_BORDERCOLOR */ STATE_RENDER(WINED3DRS_BORDERCOLOR), state_bordercolor },
2794 { /* 44, WINED3DRS_TEXTUREADDRESSU */ 0, /* Handled in ddraw */ state_undefined },
2795 { /* 45, WINED3DRS_TEXTUREADDRESSV */ 0, /* Handled in ddraw */ state_undefined },
2796 { /* 46, WINED3DRS_MIPMAPLODBIAS */ STATE_RENDER(WINED3DRS_MIPMAPLODBIAS), state_mipmaplodbias },
2797 { /* 47, WINED3DRS_ZBIAS */ STATE_RENDER(WINED3DRS_ZBIAS), state_zbias },
2798 { /* 48, WINED3DRS_RANGEFOGENABLE */ 0, state_nogl },
2799 { /* 49, WINED3DRS_ANISOTROPY */ STATE_RENDER(WINED3DRS_ANISOTROPY), state_anisotropy },
2800 { /* 50, WINED3DRS_FLUSHBATCH */ STATE_RENDER(WINED3DRS_FLUSHBATCH), state_flushbatch },
2801 { /* 51, WINED3DRS_TRANSLUCENTSORTINDEPENDENT */ STATE_RENDER(WINED3DRS_TRANSLUCENTSORTINDEPENDENT), state_translucentsi },
2802 { /* 52, WINED3DRS_STENCILENABLE */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2803 { /* 53, WINED3DRS_STENCILFAIL */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2804 { /* 54, WINED3DRS_STENCILZFAIL */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2805 { /* 55, WINED3DRS_STENCILPASS */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2806 { /* 56, WINED3DRS_STENCILFUNC */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2807 { /* 57, WINED3DRS_STENCILREF */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2808 { /* 58, WINED3DRS_STENCILMASK */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2809 { /* 59, WINED3DRS_STENCILWRITEMASK */ STATE_RENDER(WINED3DRS_STENCILWRITEMASK), state_stencilwrite },
2810 { /* 60, WINED3DRS_TEXTUREFACTOR */ STATE_RENDER(WINED3DRS_TEXTUREFACTOR), state_texfactor },
2811 { /* 61, Undefined */ 0, state_undefined },
2812 { /* 62, Undefined */ 0, state_undefined },
2813 { /* 63, Undefined */ 0, state_undefined },
2814 { /* 64, WINED3DRS_STIPPLEPATTERN00 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2815 { /* 65, WINED3DRS_STIPPLEPATTERN01 */ 0 /* Obsolete, should he handled by ddraw */, state_undefined },
2816 { /* 66, WINED3DRS_STIPPLEPATTERN02 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2817 { /* 67, WINED3DRS_STIPPLEPATTERN03 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2818 { /* 68, WINED3DRS_STIPPLEPATTERN04 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2819 { /* 69, WINED3DRS_STIPPLEPATTERN05 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2820 { /* 70, WINED3DRS_STIPPLEPATTERN06 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2821 { /* 71, WINED3DRS_STIPPLEPATTERN07 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2822 { /* 72, WINED3DRS_STIPPLEPATTERN08 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2823 { /* 73, WINED3DRS_STIPPLEPATTERN09 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2824 { /* 74, WINED3DRS_STIPPLEPATTERN10 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2825 { /* 75, WINED3DRS_STIPPLEPATTERN11 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2826 { /* 76, WINED3DRS_STIPPLEPATTERN12 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2827 { /* 77, WINED3DRS_STIPPLEPATTERN13 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2828 { /* 78, WINED3DRS_STIPPLEPATTERN14 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2829 { /* 79, WINED3DRS_STIPPLEPATTERN15 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2830 { /* 80, WINED3DRS_STIPPLEPATTERN16 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2831 { /* 81, WINED3DRS_STIPPLEPATTERN17 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2832 { /* 82, WINED3DRS_STIPPLEPATTERN18 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2833 { /* 83, WINED3DRS_STIPPLEPATTERN19 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2834 { /* 84, WINED3DRS_STIPPLEPATTERN20 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2835 { /* 85, WINED3DRS_STIPPLEPATTERN21 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2836 { /* 86, WINED3DRS_STIPPLEPATTERN22 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2837 { /* 87, WINED3DRS_STIPPLEPATTERN23 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2838 { /* 88, WINED3DRS_STIPPLEPATTERN24 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2839 { /* 89, WINED3DRS_STIPPLEPATTERN25 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2840 { /* 90, WINED3DRS_STIPPLEPATTERN26 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2841 { /* 91, WINED3DRS_STIPPLEPATTERN27 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2842 { /* 92, WINED3DRS_STIPPLEPATTERN28 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2843 { /* 93, WINED3DRS_STIPPLEPATTERN29 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2844 { /* 94, WINED3DRS_STIPPLEPATTERN30 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2845 { /* 95, WINED3DRS_STIPPLEPATTERN31 */ 0 /* Obsolete, should be handled by ddraw */, state_undefined },
2846 { /* 96, Undefined */ 0, state_undefined },
2847 { /* 97, Undefined */ 0, state_undefined },
2848 { /* 98, Undefined */ 0, state_undefined },
2849 { /* 99, Undefined */ 0, state_undefined },
2850 { /*100, Undefined */ 0, state_undefined },
2851 { /*101, Undefined */ 0, state_undefined },
2852 { /*102, Undefined */ 0, state_undefined },
2853 { /*103, Undefined */ 0, state_undefined },
2854 { /*104, Undefined */ 0, state_undefined },
2855 { /*105, Undefined */ 0, state_undefined },
2856 { /*106, Undefined */ 0, state_undefined },
2857 { /*107, Undefined */ 0, state_undefined },
2858 { /*108, Undefined */ 0, state_undefined },
2859 { /*109, Undefined */ 0, state_undefined },
2860 { /*110, Undefined */ 0, state_undefined },
2861 { /*111, Undefined */ 0, state_undefined },
2862 { /*112, Undefined */ 0, state_undefined },
2863 { /*113, Undefined */ 0, state_undefined },
2864 { /*114, Undefined */ 0, state_undefined },
2865 { /*115, Undefined */ 0, state_undefined },
2866 { /*116, Undefined */ 0, state_undefined },
2867 { /*117, Undefined */ 0, state_undefined },
2868 { /*118, Undefined */ 0, state_undefined },
2869 { /*119, Undefined */ 0, state_undefined },
2870 { /*120, Undefined */ 0, state_undefined },
2871 { /*121, Undefined */ 0, state_undefined },
2872 { /*122, Undefined */ 0, state_undefined },
2873 { /*123, Undefined */ 0, state_undefined },
2874 { /*124, Undefined */ 0, state_undefined },
2875 { /*125, Undefined */ 0, state_undefined },
2876 { /*126, Undefined */ 0, state_undefined },
2877 { /*127, Undefined */ 0, state_undefined },
2879 { /*128, WINED3DRS_WRAP0 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2880 { /*129, WINED3DRS_WRAP1 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2881 { /*130, WINED3DRS_WRAP2 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2882 { /*131, WINED3DRS_WRAP3 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2883 { /*132, WINED3DRS_WRAP4 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2884 { /*133, WINED3DRS_WRAP5 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2885 { /*134, WINED3DRS_WRAP6 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2886 { /*135, WINED3DRS_WRAP7 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2887 { /*136, WINED3DRS_CLIPPING */ STATE_RENDER(WINED3DRS_CLIPPING), state_clipping },
2888 { /*137, WINED3DRS_LIGHTING */ STATE_RENDER(WINED3DRS_LIGHTING), state_lighting },
2889 { /*138, WINED3DRS_EXTENTS */ STATE_RENDER(WINED3DRS_EXTENTS), state_extents },
2890 { /*139, WINED3DRS_AMBIENT */ STATE_RENDER(WINED3DRS_AMBIENT), state_ambient },
2891 { /*140, WINED3DRS_FOGVERTEXMODE */ STATE_RENDER(WINED3DRS_FOGENABLE), state_fog },
2892 { /*141, WINED3DRS_COLORVERTEX */ STATE_RENDER(WINED3DRS_COLORVERTEX), state_colormat },
2893 { /*142, WINED3DRS_LOCALVIEWER */ STATE_RENDER(WINED3DRS_LOCALVIEWER), state_localviewer },
2894 { /*143, WINED3DRS_NORMALIZENORMALS */ STATE_RENDER(WINED3DRS_NORMALIZENORMALS), state_normalize },
2895 { /*144, WINED3DRS_COLORKEYBLENDENABLE */ STATE_RENDER(WINED3DRS_COLORKEYBLENDENABLE), state_ckeyblend },
2896 { /*145, WINED3DRS_DIFFUSEMATERIALSOURCE */ STATE_RENDER(WINED3DRS_COLORVERTEX), state_colormat },
2897 { /*146, WINED3DRS_SPECULARMATERIALSOURCE */ STATE_RENDER(WINED3DRS_COLORVERTEX), state_colormat },
2898 { /*147, WINED3DRS_AMBIENTMATERIALSOURCE */ STATE_RENDER(WINED3DRS_COLORVERTEX), state_colormat },
2899 { /*148, WINED3DRS_EMISSIVEMATERIALSOURCE */ STATE_RENDER(WINED3DRS_COLORVERTEX), state_colormat },
2900 { /*149, Undefined */ 0, state_undefined },
2901 { /*150, Undefined */ 0, state_undefined },
2902 { /*151, WINED3DRS_VERTEXBLEND */ 0, state_nogl },
2903 { /*152, WINED3DRS_CLIPPLANEENABLE */ STATE_RENDER(WINED3DRS_CLIPPING), state_clipping },
2904 { /*153, WINED3DRS_SOFTWAREVERTEXPROCESSING */ 0, state_nogl },
2905 { /*154, WINED3DRS_POINTSIZE */ STATE_RENDER(WINED3DRS_POINTSIZE), state_psize },
2906 { /*155, WINED3DRS_POINTSIZE_MIN */ STATE_RENDER(WINED3DRS_POINTSIZE_MIN), state_psizemin },
2907 { /*156, WINED3DRS_POINTSPRITEENABLE */ STATE_RENDER(WINED3DRS_POINTSPRITEENABLE), state_pointsprite },
2908 { /*157, WINED3DRS_POINTSCALEENABLE */ STATE_RENDER(WINED3DRS_POINTSCALEENABLE), state_pscale },
2909 { /*158, WINED3DRS_POINTSCALE_A */ STATE_RENDER(WINED3DRS_POINTSCALEENABLE), state_pscale },
2910 { /*159, WINED3DRS_POINTSCALE_B */ STATE_RENDER(WINED3DRS_POINTSCALEENABLE), state_pscale },
2911 { /*160, WINED3DRS_POINTSCALE_C */ STATE_RENDER(WINED3DRS_POINTSCALEENABLE), state_pscale },
2912 { /*161, WINED3DRS_MULTISAMPLEANTIALIAS */ STATE_RENDER(WINED3DRS_MULTISAMPLEANTIALIAS), state_multisampleaa },
2913 { /*162, WINED3DRS_MULTISAMPLEMASK */ STATE_RENDER(WINED3DRS_MULTISAMPLEMASK), state_multisampmask },
2914 { /*163, WINED3DRS_PATCHEDGESTYLE */ STATE_RENDER(WINED3DRS_PATCHEDGESTYLE), state_patchedgestyle},
2915 { /*164, WINED3DRS_PATCHSEGMENTS */ STATE_RENDER(WINED3DRS_PATCHSEGMENTS), state_patchsegments },
2916 { /*165, WINED3DRS_DEBUGMONITORTOKEN */ STATE_RENDER(WINED3DRS_DEBUGMONITORTOKEN), state_nogl },
2917 { /*166, WINED3DRS_POINTSIZE_MAX */ STATE_RENDER(WINED3DRS_POINTSIZE_MAX), state_psizemax },
2918 { /*167, WINED3DRS_INDEXEDVERTEXBLENDENABLE */ 0, state_nogl },
2919 { /*168, WINED3DRS_COLORWRITEENABLE */ STATE_RENDER(WINED3DRS_COLORWRITEENABLE), state_colorwrite },
2920 { /*169, Undefined */ 0, state_undefined },
2921 { /*170, WINED3DRS_TWEENFACTOR */ 0, state_nogl },
2922 { /*171, WINED3DRS_BLENDOP */ STATE_RENDER(WINED3DRS_BLENDOP), state_blendop },
2923 { /*172, WINED3DRS_POSITIONDEGREE */ STATE_RENDER(WINED3DRS_POSITIONDEGREE), state_positiondegree},
2924 { /*173, WINED3DRS_NORMALDEGREE */ STATE_RENDER(WINED3DRS_NORMALDEGREE), state_normaldegree },
2925 /*172, WINED3DRS_POSITIONORDER */ /* Value assigned to 2 state names */
2926 /*173, WINED3DRS_NORMALORDER */ /* Value assigned to 2 state names */
2927 { /*174, WINED3DRS_SCISSORTESTENABLE */ STATE_RENDER(WINED3DRS_SCISSORTESTENABLE), state_scissor },
2928 { /*175, WINED3DRS_SLOPESCALEDEPTHBIAS */ STATE_RENDER(WINED3DRS_DEPTHBIAS), state_depthbias },
2929 { /*176, WINED3DRS_ANTIALIASEDLINEENABLE */ STATE_RENDER(WINED3DRS_ALPHABLENDENABLE), state_blend },
2930 { /*177, undefined */ 0, state_undefined },
2931 { /*178, WINED3DRS_MINTESSELLATIONLEVEL */ STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation },
2932 { /*179, WINED3DRS_MAXTESSELLATIONLEVEL */ STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation },
2933 { /*180, WINED3DRS_ADAPTIVETESS_X */ STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation },
2934 { /*181, WINED3DRS_ADAPTIVETESS_Y */ STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation },
2935 { /*182, WINED3DRS_ADAPTIVETESS_Z */ STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation },
2936 { /*183, WINED3DRS_ADAPTIVETESS_W */ STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation },
2937 { /*184, WINED3DRS_ENABLEADAPTIVETESSELLATION */ STATE_RENDER(WINED3DRS_ENABLEADAPTIVETESSELLATION), state_tessellation },
2938 { /*185, WINED3DRS_TWOSIDEDSTENCILMODE */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2939 { /*186, WINED3DRS_CCW_STENCILFAIL */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2940 { /*187, WINED3DRS_CCW_STENCILZFAIL */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2941 { /*188, WINED3DRS_CCW_STENCILPASS */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2942 { /*189, WINED3DRS_CCW_STENCILFUNC */ STATE_RENDER(WINED3DRS_STENCILENABLE), state_stencil },
2943 { /*190, WINED3DRS_COLORWRITEENABLE1 */ STATE_RENDER(WINED3DRS_COLORWRITEENABLE), state_colorwrite },
2944 { /*191, WINED3DRS_COLORWRITEENABLE2 */ STATE_RENDER(WINED3DRS_COLORWRITEENABLE), state_colorwrite },
2945 { /*192, WINED3DRS_COLORWRITEENABLE3 */ STATE_RENDER(WINED3DRS_COLORWRITEENABLE), state_colorwrite },
2946 { /*193, WINED3DRS_BLENDFACTOR */ STATE_RENDER(WINED3DRS_BLENDFACTOR), state_blendfactor },
2947 { /*194, WINED3DRS_SRGBWRITEENABLE */ STATE_RENDER(WINED3DRS_SRGBWRITEENABLE), state_srgbwrite },
2948 { /*195, WINED3DRS_DEPTHBIAS */ STATE_RENDER(WINED3DRS_DEPTHBIAS), state_depthbias },
2949 { /*196, undefined */ 0, state_undefined },
2950 { /*197, undefined */ 0, state_undefined },
2951 { /*198, WINED3DRS_WRAP8 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2952 { /*199, WINED3DRS_WRAP9 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2953 { /*200, WINED3DRS_WRAP10 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2954 { /*201, WINED3DRS_WRAP11 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2955 { /*202, WINED3DRS_WRAP12 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2956 { /*203, WINED3DRS_WRAP13 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2957 { /*204, WINED3DRS_WRAP14 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2958 { /*205, WINED3DRS_WRAP15 */ STATE_RENDER(WINED3DRS_WRAP0), state_wrap },
2959 { /*206, WINED3DRS_SEPARATEALPHABLENDENABLE */ STATE_RENDER(WINED3DRS_SEPARATEALPHABLENDENABLE), state_seperateblend },
2960 { /*207, WINED3DRS_SRCBLENDALPHA */ STATE_RENDER(WINED3DRS_SEPARATEALPHABLENDENABLE), state_seperateblend },
2961 { /*208, WINED3DRS_DESTBLENDALPHA */ STATE_RENDER(WINED3DRS_SEPARATEALPHABLENDENABLE), state_seperateblend },
2962 { /*209, WINED3DRS_BLENDOPALPHA */ STATE_RENDER(WINED3DRS_SEPARATEALPHABLENDENABLE), state_seperateblend },
2963 /* Texture stage states */
2964 { /*0, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2965 { /*0, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2966 { /*0, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2967 { /*0, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop },
2968 { /*0, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop },
2969 { /*0, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop },
2970 { /*0, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2971 { /*0, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2972 { /*0, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2973 { /*0, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2974 { /*0, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(0, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
2975 { /*0, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2976 { /*0, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2977 { /*0, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2978 { /*0, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2979 { /*0, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2980 { /*0, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2981 { /*0, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2982 { /*0, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2983 { /*0, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2984 { /*0, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2985 { /*0, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
2986 { /*0, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(0, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
2987 { /*0, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE0), transform_texture },
2988 { /*0, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2989 { /*0, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), tex_colorop },
2990 { /*0, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(0, WINED3DTSS_ALPHAOP), tex_alphaop },
2991 { /*0, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(0, WINED3DTSS_RESULTARG), tex_resultarg },
2992 { /*0, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2993 { /*0, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2994 { /*0, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
2995 { /*0, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
2997 { /*1, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
2998 { /*1, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
2999 { /*1, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
3000 { /*1, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop },
3001 { /*1, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop },
3002 { /*1, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop },
3003 { /*1, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
3004 { /*1, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
3005 { /*1, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
3006 { /*1, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
3007 { /*1, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(1, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
3008 { /*1, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3009 { /*1, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3010 { /*1, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3011 { /*1, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3012 { /*1, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3013 { /*1, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3014 { /*1, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3015 { /*1, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3016 { /*1, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3017 { /*1, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3018 { /*1, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
3019 { /*1, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(1, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
3020 { /*1, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE1), transform_texture },
3021 { /*1, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3022 { /*1, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(1, WINED3DTSS_COLOROP), tex_colorop },
3023 { /*1, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(1, WINED3DTSS_ALPHAOP), tex_alphaop },
3024 { /*1, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(1, WINED3DTSS_RESULTARG), tex_resultarg },
3025 { /*1, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3026 { /*1, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3027 { /*1, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3028 { /*1, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
3030 { /*2, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3031 { /*2, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3032 { /*2, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3033 { /*2, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop },
3034 { /*2, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop },
3035 { /*2, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop },
3036 { /*2, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3037 { /*2, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3038 { /*2, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3039 { /*2, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3040 { /*2, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(2, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
3041 { /*2, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3042 { /*2, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3043 { /*2, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3044 { /*2, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3045 { /*2, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3046 { /*2, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3047 { /*2, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3048 { /*2, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3049 { /*2, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3050 { /*2, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3051 { /*2, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
3052 { /*2, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(2, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
3053 { /*2, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE2), transform_texture },
3054 { /*2, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3055 { /*2, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(2, WINED3DTSS_COLOROP), tex_colorop },
3056 { /*2, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(2, WINED3DTSS_ALPHAOP), tex_alphaop },
3057 { /*2, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(2, WINED3DTSS_RESULTARG), tex_resultarg },
3058 { /*2, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3059 { /*2, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3060 { /*2, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3061 { /*2, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
3063 { /*3, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3064 { /*3, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3065 { /*3, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3066 { /*3, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop },
3067 { /*3, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop },
3068 { /*3, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop },
3069 { /*3, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3070 { /*3, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3071 { /*3, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3072 { /*3, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3073 { /*3, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(3, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
3074 { /*3, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3075 { /*3, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3076 { /*3, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3077 { /*3, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3078 { /*3, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3079 { /*3, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3080 { /*3, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3081 { /*3, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3082 { /*3, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3083 { /*3, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3084 { /*3, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
3085 { /*3, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(3, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
3086 { /*3, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE3), transform_texture },
3087 { /*3, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3088 { /*3, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(3, WINED3DTSS_COLOROP), tex_colorop },
3089 { /*3, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(3, WINED3DTSS_ALPHAOP), tex_alphaop },
3090 { /*3, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(3, WINED3DTSS_RESULTARG), tex_resultarg },
3091 { /*3, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3092 { /*3, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3093 { /*3, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3094 { /*3, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
3096 { /*4, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), tex_colorop },
3097 { /*4, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), tex_colorop },
3098 { /*4, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), tex_colorop },
3099 { /*4, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop },
3100 { /*4, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop },
3101 { /*4, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop },
3102 { /*4, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), state_undefined },
3103 { /*4, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), state_undefined },
3104 { /*4, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), state_undefined },
3105 { /*4, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), state_undefined },
3106 { /*4, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(4, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
3107 { /*4, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3108 { /*4, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3109 { /*4, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3110 { /*4, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3111 { /*4, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3112 { /*4, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3113 { /*4, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3114 { /*4, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3115 { /*4, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3116 { /*4, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3117 { /*4, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
3118 { /*4, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(4, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
3119 { /*4, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE4), transform_texture },
3120 { /*4, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3121 { /*4, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(4, WINED3DTSS_COLOROP), tex_colorop },
3122 { /*4, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(4, WINED3DTSS_ALPHAOP), tex_alphaop },
3123 { /*4, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(4, WINED3DTSS_RESULTARG), tex_resultarg },
3124 { /*4, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3125 { /*4, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3126 { /*4, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3127 { /*4, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
3129 { /*5, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3130 { /*5, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3131 { /*5, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3132 { /*5, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop },
3133 { /*5, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop },
3134 { /*5, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop },
3135 { /*5, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3136 { /*5, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3137 { /*5, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3138 { /*5, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3139 { /*5, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(5, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
3140 { /*5, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3141 { /*5, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3142 { /*5, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3143 { /*5, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3144 { /*5, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3145 { /*5, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3146 { /*5, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3147 { /*5, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3148 { /*5, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3149 { /*5, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3150 { /*5, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
3151 { /*5, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(5, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
3152 { /*5, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE5), transform_texture },
3153 { /*5, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3154 { /*5, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(5, WINED3DTSS_COLOROP), tex_colorop },
3155 { /*5, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(5, WINED3DTSS_ALPHAOP), tex_alphaop },
3156 { /*5, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(5, WINED3DTSS_RESULTARG), tex_resultarg },
3157 { /*5, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3158 { /*5, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3159 { /*5, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3160 { /*5, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
3162 { /*6, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3163 { /*6, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3164 { /*6, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3165 { /*6, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop },
3166 { /*6, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop },
3167 { /*6, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop },
3168 { /*6, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3169 { /*6, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3170 { /*6, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3171 { /*6, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3172 { /*6, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(6, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
3173 { /*6, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3174 { /*6, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3175 { /*6, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3176 { /*6, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3177 { /*6, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3178 { /*6, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3179 { /*6, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3180 { /*6, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3181 { /*6, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3182 { /*6, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3183 { /*6, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
3184 { /*6, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(6, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
3185 { /*6, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE6), transform_texture },
3186 { /*6, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3187 { /*6, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(6, WINED3DTSS_COLOROP), tex_colorop },
3188 { /*6, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(6, WINED3DTSS_ALPHAOP), tex_alphaop },
3189 { /*6, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(6, WINED3DTSS_RESULTARG), tex_resultarg },
3190 { /*6, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3191 { /*6, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3192 { /*6, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3193 { /*6, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
3195 { /*7, 01, WINED3DTSS_COLOROP */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3196 { /*7, 02, WINED3DTSS_COLORARG1 */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3197 { /*7, 03, WINED3DTSS_COLORARG2 */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3198 { /*7, 04, WINED3DTSS_ALPHAOP */ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop },
3199 { /*7, 05, WINED3DTSS_ALPHAARG1 */ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop },
3200 { /*7, 06, WINED3DTSS_ALPHAARG2 */ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop },
3201 { /*7, 07, WINED3DTSS_BUMPENVMAT00 */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3202 { /*7, 08, WINED3DTSS_BUMPENVMAT01 */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3203 { /*7, 09, WINED3DTSS_BUMPENVMAT10 */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3204 { /*7, 10, WINED3DTSS_BUMPENVMAT11 */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3205 { /*7, 11, WINED3DTSS_TEXCOORDINDEX */ STATE_TEXTURESTAGE(7, WINED3DTSS_TEXCOORDINDEX), tex_coordindex },
3206 { /*7, 12, WINED3DTSS_ADDRESS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3207 { /*7, 13, WINED3DTSS_ADDRESSU */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3208 { /*7, 14, WINED3DTSS_ADDRESSV */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3209 { /*7, 15, WINED3DTSS_BORDERCOLOR */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3210 { /*7, 16, WINED3DTSS_MAGFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3211 { /*7, 17, WINED3DTSS_MINFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3212 { /*7, 18, WINED3DTSS_MIPFILTER */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3213 { /*7, 19, WINED3DTSS_MIPMAPLODBIAS */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3214 { /*7, 20, WINED3DTSS_MAXMIPLEVEL */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3215 { /*7, 21, WINED3DTSS_MAXANISOTROPY */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3216 { /*7, 22, WINED3DTSS_BUMPENVLSCALE */ STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVLSCALE), tex_bumpenvlscale },
3217 { /*7, 23, WINED3DTSS_BUMPENVLOFFSET */ STATE_TEXTURESTAGE(7, WINED3DTSS_BUMPENVLOFFSET), tex_bumpenvloffset },
3218 { /*7, 24, WINED3DTSS_TEXTURETRANSFORMFLAGS */ STATE_TRANSFORM(WINED3DTS_TEXTURE7), transform_texture },
3219 { /*7, 25, WINED3DTSS_ADDRESSW */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3220 { /*7, 26, WINED3DTSS_COLORARG0 */ STATE_TEXTURESTAGE(7, WINED3DTSS_COLOROP), tex_colorop },
3221 { /*7, 27, WINED3DTSS_ALPHAARG0 */ STATE_TEXTURESTAGE(7, WINED3DTSS_ALPHAOP), tex_alphaop },
3222 { /*7, 28, WINED3DTSS_RESULTARG */ STATE_TEXTURESTAGE(7, WINED3DTSS_RESULTARG), tex_resultarg },
3223 { /*7, 29, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3224 { /*7, 30, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3225 { /*7, 31, undefined */ 0 /* -> sampler state in ddraw / d3d8 */, state_undefined },
3226 { /*7, 32, WINED3DTSS_CONSTANT */ 0 /* As long as we don't support D3DTA_CONSTANT */, state_nogl },
3227 /* Sampler states */
3228 { /* 0, Sampler 0 */ STATE_SAMPLER(0), sampler },
3229 { /* 1, Sampler 1 */ STATE_SAMPLER(1), sampler },
3230 { /* 2, Sampler 2 */ STATE_SAMPLER(2), sampler },
3231 { /* 3, Sampler 3 */ STATE_SAMPLER(3), sampler },
3232 { /* 4, Sampler 3 */ STATE_SAMPLER(4), sampler },
3233 { /* 5, Sampler 5 */ STATE_SAMPLER(5), sampler },
3234 { /* 6, Sampler 6 */ STATE_SAMPLER(6), sampler },
3235 { /* 7, Sampler 7 */ STATE_SAMPLER(7), sampler },
3236 { /* 8, Sampler 8 */ STATE_SAMPLER(8), sampler },
3237 { /* 9, Sampler 9 */ STATE_SAMPLER(9), sampler },
3238 { /*10, Sampler 10 */ STATE_SAMPLER(10), sampler },
3239 { /*11, Sampler 11 */ STATE_SAMPLER(11), sampler },
3240 { /*12, Sampler 12 */ STATE_SAMPLER(12), sampler },
3241 { /*13, Sampler 13 */ STATE_SAMPLER(13), sampler },
3242 { /*14, Sampler 14 */ STATE_SAMPLER(14), sampler },
3243 { /*15, Sampler 15 */ STATE_SAMPLER(15), sampler },
3245 { /* , Pixel Shader */ STATE_PIXELSHADER, pixelshader },
3246 /* Transform states follow */
3247 { /* 1, undefined */ 0, state_undefined },
3248 { /* 2, WINED3DTS_VIEW */ STATE_TRANSFORM(WINED3DTS_VIEW), transform_view },
3249 { /* 3, WINED3DTS_PROJECTION */ STATE_TRANSFORM(WINED3DTS_PROJECTION), transform_projection},
3250 { /* 4, undefined */ 0, state_undefined },
3251 { /* 5, undefined */ 0, state_undefined },
3252 { /* 6, undefined */ 0, state_undefined },
3253 { /* 7, undefined */ 0, state_undefined },
3254 { /* 8, undefined */ 0, state_undefined },
3255 { /* 9, undefined */ 0, state_undefined },
3256 { /* 10, undefined */ 0, state_undefined },
3257 { /* 11, undefined */ 0, state_undefined },
3258 { /* 12, undefined */ 0, state_undefined },
3259 { /* 13, undefined */ 0, state_undefined },
3260 { /* 14, undefined */ 0, state_undefined },
3261 { /* 15, undefined */ 0, state_undefined },
3262 { /* 16, WINED3DTS_TEXTURE0 */ STATE_TRANSFORM(WINED3DTS_TEXTURE0), transform_texture },
3263 { /* 17, WINED3DTS_TEXTURE1 */ STATE_TRANSFORM(WINED3DTS_TEXTURE1), transform_texture },
3264 { /* 18, WINED3DTS_TEXTURE2 */ STATE_TRANSFORM(WINED3DTS_TEXTURE2), transform_texture },
3265 { /* 19, WINED3DTS_TEXTURE3 */ STATE_TRANSFORM(WINED3DTS_TEXTURE3), transform_texture },
3266 { /* 20, WINED3DTS_TEXTURE4 */ STATE_TRANSFORM(WINED3DTS_TEXTURE4), transform_texture },
3267 { /* 21, WINED3DTS_TEXTURE5 */ STATE_TRANSFORM(WINED3DTS_TEXTURE5), transform_texture },
3268 { /* 22, WINED3DTS_TEXTURE6 */ STATE_TRANSFORM(WINED3DTS_TEXTURE6), transform_texture },
3269 { /* 23, WINED3DTS_TEXTURE7 */ STATE_TRANSFORM(WINED3DTS_TEXTURE7), transform_texture },
3270 /* A huge gap between TEXTURE7 and WORLDMATRIX(0) :-( But entries are needed to catch then if a broken app sets them */
3271 { /* 24, undefined */ 0, state_undefined },
3272 { /* 25, undefined */ 0, state_undefined },
3273 { /* 26, undefined */ 0, state_undefined },
3274 { /* 27, undefined */ 0, state_undefined },
3275 { /* 28, undefined */ 0, state_undefined },
3276 { /* 29, undefined */ 0, state_undefined },
3277 { /* 30, undefined */ 0, state_undefined },
3278 { /* 31, undefined */ 0, state_undefined },
3279 { /* 32, undefined */ 0, state_undefined },
3280 { /* 33, undefined */ 0, state_undefined },
3281 { /* 34, undefined */ 0, state_undefined },
3282 { /* 35, undefined */ 0, state_undefined },
3283 { /* 36, undefined */ 0, state_undefined },
3284 { /* 37, undefined */ 0, state_undefined },
3285 { /* 38, undefined */ 0, state_undefined },
3286 { /* 39, undefined */ 0, state_undefined },
3287 { /* 40, undefined */ 0, state_undefined },
3288 { /* 41, undefined */ 0, state_undefined },
3289 { /* 42, undefined */ 0, state_undefined },
3290 { /* 43, undefined */ 0, state_undefined },
3291 { /* 44, undefined */ 0, state_undefined },
3292 { /* 45, undefined */ 0, state_undefined },
3293 { /* 46, undefined */ 0, state_undefined },
3294 { /* 47, undefined */ 0, state_undefined },
3295 { /* 48, undefined */ 0, state_undefined },
3296 { /* 49, undefined */ 0, state_undefined },
3297 { /* 50, undefined */ 0, state_undefined },
3298 { /* 51, undefined */ 0, state_undefined },
3299 { /* 52, undefined */ 0, state_undefined },
3300 { /* 53, undefined */ 0, state_undefined },
3301 { /* 54, undefined */ 0, state_undefined },
3302 { /* 55, undefined */ 0, state_undefined },
3303 { /* 56, undefined */ 0, state_undefined },
3304 { /* 57, undefined */ 0, state_undefined },
3305 { /* 58, undefined */ 0, state_undefined },
3306 { /* 59, undefined */ 0, state_undefined },
3307 { /* 60, undefined */ 0, state_undefined },
3308 { /* 61, undefined */ 0, state_undefined },
3309 { /* 62, undefined */ 0, state_undefined },
3310 { /* 63, undefined */ 0, state_undefined },
3311 { /* 64, undefined */ 0, state_undefined },
3312 { /* 65, undefined */ 0, state_undefined },
3313 { /* 66, undefined */ 0, state_undefined },
3314 { /* 67, undefined */ 0, state_undefined },
3315 { /* 68, undefined */ 0, state_undefined },
3316 { /* 69, undefined */ 0, state_undefined },
3317 { /* 70, undefined */ 0, state_undefined },
3318 { /* 71, undefined */ 0, state_undefined },
3319 { /* 72, undefined */ 0, state_undefined },
3320 { /* 73, undefined */ 0, state_undefined },
3321 { /* 74, undefined */ 0, state_undefined },
3322 { /* 75, undefined */ 0, state_undefined },
3323 { /* 76, undefined */ 0, state_undefined },
3324 { /* 77, undefined */ 0, state_undefined },
3325 { /* 78, undefined */ 0, state_undefined },
3326 { /* 79, undefined */ 0, state_undefined },
3327 { /* 80, undefined */ 0, state_undefined },
3328 { /* 81, undefined */ 0, state_undefined },
3329 { /* 82, undefined */ 0, state_undefined },
3330 { /* 83, undefined */ 0, state_undefined },
3331 { /* 84, undefined */ 0, state_undefined },
3332 { /* 85, undefined */ 0, state_undefined },
3333 { /* 86, undefined */ 0, state_undefined },
3334 { /* 87, undefined */ 0, state_undefined },
3335 { /* 88, undefined */ 0, state_undefined },
3336 { /* 89, undefined */ 0, state_undefined },
3337 { /* 90, undefined */ 0, state_undefined },
3338 { /* 91, undefined */ 0, state_undefined },
3339 { /* 92, undefined */ 0, state_undefined },
3340 { /* 93, undefined */ 0, state_undefined },
3341 { /* 94, undefined */ 0, state_undefined },
3342 { /* 95, undefined */ 0, state_undefined },
3343 { /* 96, undefined */ 0, state_undefined },
3344 { /* 97, undefined */ 0, state_undefined },
3345 { /* 98, undefined */ 0, state_undefined },
3346 { /* 99, undefined */ 0, state_undefined },
3347 { /*100, undefined */ 0, state_undefined },
3348 { /*101, undefined */ 0, state_undefined },
3349 { /*102, undefined */ 0, state_undefined },
3350 { /*103, undefined */ 0, state_undefined },
3351 { /*104, undefined */ 0, state_undefined },
3352 { /*105, undefined */ 0, state_undefined },
3353 { /*106, undefined */ 0, state_undefined },
3354 { /*107, undefined */ 0, state_undefined },
3355 { /*108, undefined */ 0, state_undefined },
3356 { /*109, undefined */ 0, state_undefined },
3357 { /*110, undefined */ 0, state_undefined },
3358 { /*111, undefined */ 0, state_undefined },
3359 { /*112, undefined */ 0, state_undefined },
3360 { /*113, undefined */ 0, state_undefined },
3361 { /*114, undefined */ 0, state_undefined },
3362 { /*115, undefined */ 0, state_undefined },
3363 { /*116, undefined */ 0, state_undefined },
3364 { /*117, undefined */ 0, state_undefined },
3365 { /*118, undefined */ 0, state_undefined },
3366 { /*119, undefined */ 0, state_undefined },
3367 { /*120, undefined */ 0, state_undefined },
3368 { /*121, undefined */ 0, state_undefined },
3369 { /*122, undefined */ 0, state_undefined },
3370 { /*123, undefined */ 0, state_undefined },
3371 { /*124, undefined */ 0, state_undefined },
3372 { /*125, undefined */ 0, state_undefined },
3373 { /*126, undefined */ 0, state_undefined },
3374 { /*127, undefined */ 0, state_undefined },
3375 { /*128, undefined */ 0, state_undefined },
3376 { /*129, undefined */ 0, state_undefined },
3377 { /*130, undefined */ 0, state_undefined },
3378 { /*131, undefined */ 0, state_undefined },
3379 { /*132, undefined */ 0, state_undefined },
3380 { /*133, undefined */ 0, state_undefined },
3381 { /*134, undefined */ 0, state_undefined },
3382 { /*135, undefined */ 0, state_undefined },
3383 { /*136, undefined */ 0, state_undefined },
3384 { /*137, undefined */ 0, state_undefined },
3385 { /*138, undefined */ 0, state_undefined },
3386 { /*139, undefined */ 0, state_undefined },
3387 { /*140, undefined */ 0, state_undefined },
3388 { /*141, undefined */ 0, state_undefined },
3389 { /*142, undefined */ 0, state_undefined },
3390 { /*143, undefined */ 0, state_undefined },
3391 { /*144, undefined */ 0, state_undefined },
3392 { /*145, undefined */ 0, state_undefined },
3393 { /*146, undefined */ 0, state_undefined },
3394 { /*147, undefined */ 0, state_undefined },
3395 { /*148, undefined */ 0, state_undefined },
3396 { /*149, undefined */ 0, state_undefined },
3397 { /*150, undefined */ 0, state_undefined },
3398 { /*151, undefined */ 0, state_undefined },
3399 { /*152, undefined */ 0, state_undefined },
3400 { /*153, undefined */ 0, state_undefined },
3401 { /*154, undefined */ 0, state_undefined },
3402 { /*155, undefined */ 0, state_undefined },
3403 { /*156, undefined */ 0, state_undefined },
3404 { /*157, undefined */ 0, state_undefined },
3405 { /*158, undefined */ 0, state_undefined },
3406 { /*159, undefined */ 0, state_undefined },
3407 { /*160, undefined */ 0, state_undefined },
3408 { /*161, undefined */ 0, state_undefined },
3409 { /*162, undefined */ 0, state_undefined },
3410 { /*163, undefined */ 0, state_undefined },
3411 { /*164, undefined */ 0, state_undefined },
3412 { /*165, undefined */ 0, state_undefined },
3413 { /*166, undefined */ 0, state_undefined },
3414 { /*167, undefined */ 0, state_undefined },
3415 { /*168, undefined */ 0, state_undefined },
3416 { /*169, undefined */ 0, state_undefined },
3417 { /*170, undefined */ 0, state_undefined },
3418 { /*171, undefined */ 0, state_undefined },
3419 { /*172, undefined */ 0, state_undefined },
3420 { /*173, undefined */ 0, state_undefined },
3421 { /*174, undefined */ 0, state_undefined },
3422 { /*175, undefined */ 0, state_undefined },
3423 { /*176, undefined */ 0, state_undefined },
3424 { /*177, undefined */ 0, state_undefined },
3425 { /*178, undefined */ 0, state_undefined },
3426 { /*179, undefined */ 0, state_undefined },
3427 { /*180, undefined */ 0, state_undefined },
3428 { /*181, undefined */ 0, state_undefined },
3429 { /*182, undefined */ 0, state_undefined },
3430 { /*183, undefined */ 0, state_undefined },
3431 { /*184, undefined */ 0, state_undefined },
3432 { /*185, undefined */ 0, state_undefined },
3433 { /*186, undefined */ 0, state_undefined },
3434 { /*187, undefined */ 0, state_undefined },
3435 { /*188, undefined */ 0, state_undefined },
3436 { /*189, undefined */ 0, state_undefined },
3437 { /*190, undefined */ 0, state_undefined },
3438 { /*191, undefined */ 0, state_undefined },
3439 { /*192, undefined */ 0, state_undefined },
3440 { /*193, undefined */ 0, state_undefined },
3441 { /*194, undefined */ 0, state_undefined },
3442 { /*195, undefined */ 0, state_undefined },
3443 { /*196, undefined */ 0, state_undefined },
3444 { /*197, undefined */ 0, state_undefined },
3445 { /*198, undefined */ 0, state_undefined },
3446 { /*199, undefined */ 0, state_undefined },
3447 { /*200, undefined */ 0, state_undefined },
3448 { /*201, undefined */ 0, state_undefined },
3449 { /*202, undefined */ 0, state_undefined },
3450 { /*203, undefined */ 0, state_undefined },
3451 { /*204, undefined */ 0, state_undefined },
3452 { /*205, undefined */ 0, state_undefined },
3453 { /*206, undefined */ 0, state_undefined },
3454 { /*207, undefined */ 0, state_undefined },
3455 { /*208, undefined */ 0, state_undefined },
3456 { /*209, undefined */ 0, state_undefined },
3457 { /*210, undefined */ 0, state_undefined },
3458 { /*211, undefined */ 0, state_undefined },
3459 { /*212, undefined */ 0, state_undefined },
3460 { /*213, undefined */ 0, state_undefined },
3461 { /*214, undefined */ 0, state_undefined },
3462 { /*215, undefined */ 0, state_undefined },
3463 { /*216, undefined */ 0, state_undefined },
3464 { /*217, undefined */ 0, state_undefined },
3465 { /*218, undefined */ 0, state_undefined },
3466 { /*219, undefined */ 0, state_undefined },
3467 { /*220, undefined */ 0, state_undefined },
3468 { /*221, undefined */ 0, state_undefined },
3469 { /*222, undefined */ 0, state_undefined },
3470 { /*223, undefined */ 0, state_undefined },
3471 { /*224, undefined */ 0, state_undefined },
3472 { /*225, undefined */ 0, state_undefined },
3473 { /*226, undefined */ 0, state_undefined },
3474 { /*227, undefined */ 0, state_undefined },
3475 { /*228, undefined */ 0, state_undefined },
3476 { /*229, undefined */ 0, state_undefined },
3477 { /*230, undefined */ 0, state_undefined },
3478 { /*231, undefined */ 0, state_undefined },
3479 { /*232, undefined */ 0, state_undefined },
3480 { /*233, undefined */ 0, state_undefined },
3481 { /*234, undefined */ 0, state_undefined },
3482 { /*235, undefined */ 0, state_undefined },
3483 { /*236, undefined */ 0, state_undefined },
3484 { /*237, undefined */ 0, state_undefined },
3485 { /*238, undefined */ 0, state_undefined },
3486 { /*239, undefined */ 0, state_undefined },
3487 { /*240, undefined */ 0, state_undefined },
3488 { /*241, undefined */ 0, state_undefined },
3489 { /*242, undefined */ 0, state_undefined },
3490 { /*243, undefined */ 0, state_undefined },
3491 { /*244, undefined */ 0, state_undefined },
3492 { /*245, undefined */ 0, state_undefined },
3493 { /*246, undefined */ 0, state_undefined },
3494 { /*247, undefined */ 0, state_undefined },
3495 { /*248, undefined */ 0, state_undefined },
3496 { /*249, undefined */ 0, state_undefined },
3497 { /*250, undefined */ 0, state_undefined },
3498 { /*251, undefined */ 0, state_undefined },
3499 { /*252, undefined */ 0, state_undefined },
3500 { /*253, undefined */ 0, state_undefined },
3501 { /*254, undefined */ 0, state_undefined },
3502 { /*255, undefined */ 0, state_undefined },
3504 { /*256, WINED3DTS_WORLDMATRIX(0) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(0)), transform_world },
3505 { /*257, WINED3DTS_WORLDMATRIX(1) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(1)), transform_worldex },
3506 { /*258, WINED3DTS_WORLDMATRIX(2) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(2)), transform_worldex },
3507 { /*259, WINED3DTS_WORLDMATRIX(3) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(3)), transform_worldex },
3508 { /*260, WINED3DTS_WORLDMATRIX(4) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(4)), transform_worldex },
3509 { /*261, WINED3DTS_WORLDMATRIX(5) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(5)), transform_worldex },
3510 { /*262, WINED3DTS_WORLDMATRIX(6) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(6)), transform_worldex },
3511 { /*263, WINED3DTS_WORLDMATRIX(7) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(7)), transform_worldex },
3512 { /*264, WINED3DTS_WORLDMATRIX(8) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(8)), transform_worldex },
3513 { /*265, WINED3DTS_WORLDMATRIX(9) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(9)), transform_worldex },
3514 { /*266, WINED3DTS_WORLDMATRIX(10) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(10)), transform_worldex },
3515 { /*267, WINED3DTS_WORLDMATRIX(11) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(11)), transform_worldex },
3516 { /*268, WINED3DTS_WORLDMATRIX(12) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(12)), transform_worldex },
3517 { /*269, WINED3DTS_WORLDMATRIX(13) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(13)), transform_worldex },
3518 { /*270, WINED3DTS_WORLDMATRIX(14) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(14)), transform_worldex },
3519 { /*271, WINED3DTS_WORLDMATRIX(15) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(15)), transform_worldex },
3520 { /*272, WINED3DTS_WORLDMATRIX(16) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(16)), transform_worldex },
3521 { /*273, WINED3DTS_WORLDMATRIX(17) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(17)), transform_worldex },
3522 { /*274, WINED3DTS_WORLDMATRIX(18) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(18)), transform_worldex },
3523 { /*275, WINED3DTS_WORLDMATRIX(19) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(19)), transform_worldex },
3524 { /*276, WINED3DTS_WORLDMATRIX(20) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(20)), transform_worldex },
3525 { /*277, WINED3DTS_WORLDMATRIX(21) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(21)), transform_worldex },
3526 { /*278, WINED3DTS_WORLDMATRIX(22) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(22)), transform_worldex },
3527 { /*279, WINED3DTS_WORLDMATRIX(23) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(23)), transform_worldex },
3528 { /*280, WINED3DTS_WORLDMATRIX(24) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(24)), transform_worldex },
3529 { /*281, WINED3DTS_WORLDMATRIX(25) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(25)), transform_worldex },
3530 { /*282, WINED3DTS_WORLDMATRIX(26) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(26)), transform_worldex },
3531 { /*283, WINED3DTS_WORLDMATRIX(27) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(27)), transform_worldex },
3532 { /*284, WINED3DTS_WORLDMATRIX(28) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(28)), transform_worldex },
3533 { /*285, WINED3DTS_WORLDMATRIX(29) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(29)), transform_worldex },
3534 { /*286, WINED3DTS_WORLDMATRIX(30) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(30)), transform_worldex },
3535 { /*287, WINED3DTS_WORLDMATRIX(31) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(31)), transform_worldex },
3536 { /*288, WINED3DTS_WORLDMATRIX(32) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(32)), transform_worldex },
3537 { /*289, WINED3DTS_WORLDMATRIX(33) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(33)), transform_worldex },
3538 { /*290, WINED3DTS_WORLDMATRIX(34) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(34)), transform_worldex },
3539 { /*291, WINED3DTS_WORLDMATRIX(35) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(35)), transform_worldex },
3540 { /*292, WINED3DTS_WORLDMATRIX(36) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(36)), transform_worldex },
3541 { /*293, WINED3DTS_WORLDMATRIX(37) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(37)), transform_worldex },
3542 { /*294, WINED3DTS_WORLDMATRIX(38) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(38)), transform_worldex },
3543 { /*295, WINED3DTS_WORLDMATRIX(39) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(39)), transform_worldex },
3544 { /*296, WINED3DTS_WORLDMATRIX(40) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(40)), transform_worldex },
3545 { /*297, WINED3DTS_WORLDMATRIX(41) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(41)), transform_worldex },
3546 { /*298, WINED3DTS_WORLDMATRIX(42) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(42)), transform_worldex },
3547 { /*299, WINED3DTS_WORLDMATRIX(43) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(43)), transform_worldex },
3548 { /*300, WINED3DTS_WORLDMATRIX(44) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(44)), transform_worldex },
3549 { /*301, WINED3DTS_WORLDMATRIX(45) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(45)), transform_worldex },
3550 { /*302, WINED3DTS_WORLDMATRIX(46) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(46)), transform_worldex },
3551 { /*303, WINED3DTS_WORLDMATRIX(47) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(47)), transform_worldex },
3552 { /*304, WINED3DTS_WORLDMATRIX(48) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(48)), transform_worldex },
3553 { /*305, WINED3DTS_WORLDMATRIX(49) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(49)), transform_worldex },
3554 { /*306, WINED3DTS_WORLDMATRIX(50) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(50)), transform_worldex },
3555 { /*307, WINED3DTS_WORLDMATRIX(51) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(51)), transform_worldex },
3556 { /*308, WINED3DTS_WORLDMATRIX(52) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(52)), transform_worldex },
3557 { /*309, WINED3DTS_WORLDMATRIX(53) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(53)), transform_worldex },
3558 { /*310, WINED3DTS_WORLDMATRIX(54) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(54)), transform_worldex },
3559 { /*311, WINED3DTS_WORLDMATRIX(55) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(55)), transform_worldex },
3560 { /*312, WINED3DTS_WORLDMATRIX(56) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(56)), transform_worldex },
3561 { /*313, WINED3DTS_WORLDMATRIX(57) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(57)), transform_worldex },
3562 { /*314, WINED3DTS_WORLDMATRIX(58) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(58)), transform_worldex },
3563 { /*315, WINED3DTS_WORLDMATRIX(59) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(59)), transform_worldex },
3564 { /*316, WINED3DTS_WORLDMATRIX(60) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(60)), transform_worldex },
3565 { /*317, WINED3DTS_WORLDMATRIX(61) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(61)), transform_worldex },
3566 { /*318, WINED3DTS_WORLDMATRIX(62) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(62)), transform_worldex },
3567 { /*319, WINED3DTS_WORLDMATRIX(63) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(63)), transform_worldex },
3568 { /*320, WINED3DTS_WORLDMATRIX(64) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(64)), transform_worldex },
3569 { /*321, WINED3DTS_WORLDMATRIX(65) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(65)), transform_worldex },
3570 { /*322, WINED3DTS_WORLDMATRIX(66) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(66)), transform_worldex },
3571 { /*323, WINED3DTS_WORLDMATRIX(67) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(67)), transform_worldex },
3572 { /*324, WINED3DTS_WORLDMATRIX(68) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(68)), transform_worldex },
3573 { /*325, WINED3DTS_WORLDMATRIX(68) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(69)), transform_worldex },
3574 { /*326, WINED3DTS_WORLDMATRIX(70) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(70)), transform_worldex },
3575 { /*327, WINED3DTS_WORLDMATRIX(71) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(71)), transform_worldex },
3576 { /*328, WINED3DTS_WORLDMATRIX(72) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(72)), transform_worldex },
3577 { /*329, WINED3DTS_WORLDMATRIX(73) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(73)), transform_worldex },
3578 { /*330, WINED3DTS_WORLDMATRIX(74) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(74)), transform_worldex },
3579 { /*331, WINED3DTS_WORLDMATRIX(75) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(75)), transform_worldex },
3580 { /*332, WINED3DTS_WORLDMATRIX(76) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(76)), transform_worldex },
3581 { /*333, WINED3DTS_WORLDMATRIX(77) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(77)), transform_worldex },
3582 { /*334, WINED3DTS_WORLDMATRIX(78) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(78)), transform_worldex },
3583 { /*335, WINED3DTS_WORLDMATRIX(79) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(79)), transform_worldex },
3584 { /*336, WINED3DTS_WORLDMATRIX(80) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(80)), transform_worldex },
3585 { /*337, WINED3DTS_WORLDMATRIX(81) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(81)), transform_worldex },
3586 { /*338, WINED3DTS_WORLDMATRIX(82) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(82)), transform_worldex },
3587 { /*339, WINED3DTS_WORLDMATRIX(83) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(83)), transform_worldex },
3588 { /*340, WINED3DTS_WORLDMATRIX(84) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(84)), transform_worldex },
3589 { /*341, WINED3DTS_WORLDMATRIX(85) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(85)), transform_worldex },
3590 { /*341, WINED3DTS_WORLDMATRIX(86) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(86)), transform_worldex },
3591 { /*343, WINED3DTS_WORLDMATRIX(87) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(87)), transform_worldex },
3592 { /*344, WINED3DTS_WORLDMATRIX(88) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(88)), transform_worldex },
3593 { /*345, WINED3DTS_WORLDMATRIX(89) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(89)), transform_worldex },
3594 { /*346, WINED3DTS_WORLDMATRIX(90) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(90)), transform_worldex },
3595 { /*347, WINED3DTS_WORLDMATRIX(91) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(91)), transform_worldex },
3596 { /*348, WINED3DTS_WORLDMATRIX(92) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(92)), transform_worldex },
3597 { /*349, WINED3DTS_WORLDMATRIX(93) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(93)), transform_worldex },
3598 { /*350, WINED3DTS_WORLDMATRIX(94) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(94)), transform_worldex },
3599 { /*351, WINED3DTS_WORLDMATRIX(95) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(95)), transform_worldex },
3600 { /*352, WINED3DTS_WORLDMATRIX(96) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(96)), transform_worldex },
3601 { /*353, WINED3DTS_WORLDMATRIX(97) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(97)), transform_worldex },
3602 { /*354, WINED3DTS_WORLDMATRIX(98) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(98)), transform_worldex },
3603 { /*355, WINED3DTS_WORLDMATRIX(99) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(99)), transform_worldex },
3604 { /*356, WINED3DTS_WORLDMATRIX(100) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(100)), transform_worldex },
3605 { /*357, WINED3DTS_WORLDMATRIX(101) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(101)), transform_worldex },
3606 { /*358, WINED3DTS_WORLDMATRIX(102) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(102)), transform_worldex },
3607 { /*359, WINED3DTS_WORLDMATRIX(103) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(103)), transform_worldex },
3608 { /*360, WINED3DTS_WORLDMATRIX(104) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(104)), transform_worldex },
3609 { /*361, WINED3DTS_WORLDMATRIX(105) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(105)), transform_worldex },
3610 { /*362, WINED3DTS_WORLDMATRIX(106) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(106)), transform_worldex },
3611 { /*363, WINED3DTS_WORLDMATRIX(107) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(107)), transform_worldex },
3612 { /*364, WINED3DTS_WORLDMATRIX(108) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(108)), transform_worldex },
3613 { /*365, WINED3DTS_WORLDMATRIX(109) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(109)), transform_worldex },
3614 { /*366, WINED3DTS_WORLDMATRIX(110) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(110)), transform_worldex },
3615 { /*367, WINED3DTS_WORLDMATRIX(111) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(111)), transform_worldex },
3616 { /*368, WINED3DTS_WORLDMATRIX(112) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(112)), transform_worldex },
3617 { /*369, WINED3DTS_WORLDMATRIX(113) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(113)), transform_worldex },
3618 { /*370, WINED3DTS_WORLDMATRIX(114) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(114)), transform_worldex },
3619 { /*371, WINED3DTS_WORLDMATRIX(115) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(115)), transform_worldex },
3620 { /*372, WINED3DTS_WORLDMATRIX(116) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(116)), transform_worldex },
3621 { /*373, WINED3DTS_WORLDMATRIX(117) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(117)), transform_worldex },
3622 { /*374, WINED3DTS_WORLDMATRIX(118) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(118)), transform_worldex },
3623 { /*375, WINED3DTS_WORLDMATRIX(119) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(119)), transform_worldex },
3624 { /*376, WINED3DTS_WORLDMATRIX(120) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(120)), transform_worldex },
3625 { /*377, WINED3DTS_WORLDMATRIX(121) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(121)), transform_worldex },
3626 { /*378, WINED3DTS_WORLDMATRIX(122) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(122)), transform_worldex },
3627 { /*379, WINED3DTS_WORLDMATRIX(123) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(123)), transform_worldex },
3628 { /*380, WINED3DTS_WORLDMATRIX(124) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(124)), transform_worldex },
3629 { /*381, WINED3DTS_WORLDMATRIX(125) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(125)), transform_worldex },
3630 { /*382, WINED3DTS_WORLDMATRIX(126) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(126)), transform_worldex },
3631 { /*383, WINED3DTS_WORLDMATRIX(127) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(127)), transform_worldex },
3632 { /*384, WINED3DTS_WORLDMATRIX(128) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(128)), transform_worldex },
3633 { /*385, WINED3DTS_WORLDMATRIX(129) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(129)), transform_worldex },
3634 { /*386, WINED3DTS_WORLDMATRIX(130) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(130)), transform_worldex },
3635 { /*387, WINED3DTS_WORLDMATRIX(131) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(131)), transform_worldex },
3636 { /*388, WINED3DTS_WORLDMATRIX(132) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(132)), transform_worldex },
3637 { /*389, WINED3DTS_WORLDMATRIX(133) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(133)), transform_worldex },
3638 { /*390, WINED3DTS_WORLDMATRIX(134) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(134)), transform_worldex },
3639 { /*391, WINED3DTS_WORLDMATRIX(135) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(135)), transform_worldex },
3640 { /*392, WINED3DTS_WORLDMATRIX(136) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(136)), transform_worldex },
3641 { /*393, WINED3DTS_WORLDMATRIX(137) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(137)), transform_worldex },
3642 { /*394, WINED3DTS_WORLDMATRIX(138) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(138)), transform_worldex },
3643 { /*395, WINED3DTS_WORLDMATRIX(139) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(139)), transform_worldex },
3644 { /*396, WINED3DTS_WORLDMATRIX(140) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(140)), transform_worldex },
3645 { /*397, WINED3DTS_WORLDMATRIX(141) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(141)), transform_worldex },
3646 { /*398, WINED3DTS_WORLDMATRIX(142) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(142)), transform_worldex },
3647 { /*399, WINED3DTS_WORLDMATRIX(143) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(143)), transform_worldex },
3648 { /*400, WINED3DTS_WORLDMATRIX(144) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(144)), transform_worldex },
3649 { /*401, WINED3DTS_WORLDMATRIX(145) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(145)), transform_worldex },
3650 { /*402, WINED3DTS_WORLDMATRIX(146) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(146)), transform_worldex },
3651 { /*403, WINED3DTS_WORLDMATRIX(147) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(147)), transform_worldex },
3652 { /*404, WINED3DTS_WORLDMATRIX(148) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(148)), transform_worldex },
3653 { /*405, WINED3DTS_WORLDMATRIX(149) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(149)), transform_worldex },
3654 { /*406, WINED3DTS_WORLDMATRIX(150) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(150)), transform_worldex },
3655 { /*407, WINED3DTS_WORLDMATRIX(151) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(151)), transform_worldex },
3656 { /*408, WINED3DTS_WORLDMATRIX(152) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(152)), transform_worldex },
3657 { /*409, WINED3DTS_WORLDMATRIX(153) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(153)), transform_worldex },
3658 { /*410, WINED3DTS_WORLDMATRIX(154) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(154)), transform_worldex },
3659 { /*411, WINED3DTS_WORLDMATRIX(155) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(155)), transform_worldex },
3660 { /*412, WINED3DTS_WORLDMATRIX(156) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(156)), transform_worldex },
3661 { /*413, WINED3DTS_WORLDMATRIX(157) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(157)), transform_worldex },
3662 { /*414, WINED3DTS_WORLDMATRIX(158) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(158)), transform_worldex },
3663 { /*415, WINED3DTS_WORLDMATRIX(159) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(159)), transform_worldex },
3664 { /*416, WINED3DTS_WORLDMATRIX(160) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(160)), transform_worldex },
3665 { /*417, WINED3DTS_WORLDMATRIX(161) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(161)), transform_worldex },
3666 { /*418, WINED3DTS_WORLDMATRIX(162) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(162)), transform_worldex },
3667 { /*419, WINED3DTS_WORLDMATRIX(163) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(163)), transform_worldex },
3668 { /*420, WINED3DTS_WORLDMATRIX(164) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(164)), transform_worldex },
3669 { /*421, WINED3DTS_WORLDMATRIX(165) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(165)), transform_worldex },
3670 { /*422, WINED3DTS_WORLDMATRIX(166) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(166)), transform_worldex },
3671 { /*423, WINED3DTS_WORLDMATRIX(167) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(167)), transform_worldex },
3672 { /*424, WINED3DTS_WORLDMATRIX(168) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(168)), transform_worldex },
3673 { /*425, WINED3DTS_WORLDMATRIX(168) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(169)), transform_worldex },
3674 { /*426, WINED3DTS_WORLDMATRIX(170) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(170)), transform_worldex },
3675 { /*427, WINED3DTS_WORLDMATRIX(171) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(171)), transform_worldex },
3676 { /*428, WINED3DTS_WORLDMATRIX(172) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(172)), transform_worldex },
3677 { /*429, WINED3DTS_WORLDMATRIX(173) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(173)), transform_worldex },
3678 { /*430, WINED3DTS_WORLDMATRIX(174) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(174)), transform_worldex },
3679 { /*431, WINED3DTS_WORLDMATRIX(175) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(175)), transform_worldex },
3680 { /*432, WINED3DTS_WORLDMATRIX(176) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(176)), transform_worldex },
3681 { /*433, WINED3DTS_WORLDMATRIX(177) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(177)), transform_worldex },
3682 { /*434, WINED3DTS_WORLDMATRIX(178) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(178)), transform_worldex },
3683 { /*435, WINED3DTS_WORLDMATRIX(179) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(179)), transform_worldex },
3684 { /*436, WINED3DTS_WORLDMATRIX(180) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(180)), transform_worldex },
3685 { /*437, WINED3DTS_WORLDMATRIX(181) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(181)), transform_worldex },
3686 { /*438, WINED3DTS_WORLDMATRIX(182) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(182)), transform_worldex },
3687 { /*439, WINED3DTS_WORLDMATRIX(183) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(183)), transform_worldex },
3688 { /*440, WINED3DTS_WORLDMATRIX(184) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(184)), transform_worldex },
3689 { /*441, WINED3DTS_WORLDMATRIX(185) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(185)), transform_worldex },
3690 { /*441, WINED3DTS_WORLDMATRIX(186) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(186)), transform_worldex },
3691 { /*443, WINED3DTS_WORLDMATRIX(187) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(187)), transform_worldex },
3692 { /*444, WINED3DTS_WORLDMATRIX(188) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(188)), transform_worldex },
3693 { /*445, WINED3DTS_WORLDMATRIX(189) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(189)), transform_worldex },
3694 { /*446, WINED3DTS_WORLDMATRIX(190) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(190)), transform_worldex },
3695 { /*447, WINED3DTS_WORLDMATRIX(191) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(191)), transform_worldex },
3696 { /*448, WINED3DTS_WORLDMATRIX(192) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(192)), transform_worldex },
3697 { /*449, WINED3DTS_WORLDMATRIX(193) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(193)), transform_worldex },
3698 { /*450, WINED3DTS_WORLDMATRIX(194) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(194)), transform_worldex },
3699 { /*451, WINED3DTS_WORLDMATRIX(195) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(195)), transform_worldex },
3700 { /*452, WINED3DTS_WORLDMATRIX(196) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(196)), transform_worldex },
3701 { /*453, WINED3DTS_WORLDMATRIX(197) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(197)), transform_worldex },
3702 { /*454, WINED3DTS_WORLDMATRIX(198) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(198)), transform_worldex },
3703 { /*455, WINED3DTS_WORLDMATRIX(199) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(199)), transform_worldex },
3704 { /*356, WINED3DTS_WORLDMATRIX(200) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(200)), transform_worldex },
3705 { /*457, WINED3DTS_WORLDMATRIX(201) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(201)), transform_worldex },
3706 { /*458, WINED3DTS_WORLDMATRIX(202) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(202)), transform_worldex },
3707 { /*459, WINED3DTS_WORLDMATRIX(203) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(203)), transform_worldex },
3708 { /*460, WINED3DTS_WORLDMATRIX(204) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(204)), transform_worldex },
3709 { /*461, WINED3DTS_WORLDMATRIX(205) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(205)), transform_worldex },
3710 { /*462, WINED3DTS_WORLDMATRIX(206) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(206)), transform_worldex },
3711 { /*463, WINED3DTS_WORLDMATRIX(207) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(207)), transform_worldex },
3712 { /*464, WINED3DTS_WORLDMATRIX(208) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(208)), transform_worldex },
3713 { /*465, WINED3DTS_WORLDMATRIX(209) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(209)), transform_worldex },
3714 { /*466, WINED3DTS_WORLDMATRIX(210) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(210)), transform_worldex },
3715 { /*467, WINED3DTS_WORLDMATRIX(211) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(211)), transform_worldex },
3716 { /*468, WINED3DTS_WORLDMATRIX(212) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(212)), transform_worldex },
3717 { /*469, WINED3DTS_WORLDMATRIX(213) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(213)), transform_worldex },
3718 { /*470, WINED3DTS_WORLDMATRIX(214) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(214)), transform_worldex },
3719 { /*471, WINED3DTS_WORLDMATRIX(215) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(215)), transform_worldex },
3720 { /*472, WINED3DTS_WORLDMATRIX(216) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(216)), transform_worldex },
3721 { /*473, WINED3DTS_WORLDMATRIX(217) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(217)), transform_worldex },
3722 { /*474, WINED3DTS_WORLDMATRIX(218) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(218)), transform_worldex },
3723 { /*475, WINED3DTS_WORLDMATRIX(219) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(219)), transform_worldex },
3724 { /*476, WINED3DTS_WORLDMATRIX(220) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(220)), transform_worldex },
3725 { /*477, WINED3DTS_WORLDMATRIX(221) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(221)), transform_worldex },
3726 { /*478, WINED3DTS_WORLDMATRIX(222) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(222)), transform_worldex },
3727 { /*479, WINED3DTS_WORLDMATRIX(223) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(223)), transform_worldex },
3728 { /*480, WINED3DTS_WORLDMATRIX(224) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(224)), transform_worldex },
3729 { /*481, WINED3DTS_WORLDMATRIX(225) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(225)), transform_worldex },
3730 { /*482, WINED3DTS_WORLDMATRIX(226) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(226)), transform_worldex },
3731 { /*483, WINED3DTS_WORLDMATRIX(227) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(227)), transform_worldex },
3732 { /*484, WINED3DTS_WORLDMATRIX(228) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(228)), transform_worldex },
3733 { /*485, WINED3DTS_WORLDMATRIX(229) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(229)), transform_worldex },
3734 { /*486, WINED3DTS_WORLDMATRIX(230) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(230)), transform_worldex },
3735 { /*487, WINED3DTS_WORLDMATRIX(231) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(231)), transform_worldex },
3736 { /*488, WINED3DTS_WORLDMATRIX(232) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(232)), transform_worldex },
3737 { /*489, WINED3DTS_WORLDMATRIX(233) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(233)), transform_worldex },
3738 { /*490, WINED3DTS_WORLDMATRIX(234) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(234)), transform_worldex },
3739 { /*491, WINED3DTS_WORLDMATRIX(235) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(235)), transform_worldex },
3740 { /*492, WINED3DTS_WORLDMATRIX(236) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(236)), transform_worldex },
3741 { /*493, WINED3DTS_WORLDMATRIX(237) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(237)), transform_worldex },
3742 { /*494, WINED3DTS_WORLDMATRIX(238) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(238)), transform_worldex },
3743 { /*495, WINED3DTS_WORLDMATRIX(239) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(239)), transform_worldex },
3744 { /*496, WINED3DTS_WORLDMATRIX(240) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(240)), transform_worldex },
3745 { /*497, WINED3DTS_WORLDMATRIX(241) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(241)), transform_worldex },
3746 { /*498, WINED3DTS_WORLDMATRIX(242) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(242)), transform_worldex },
3747 { /*499, WINED3DTS_WORLDMATRIX(243) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(243)), transform_worldex },
3748 { /*500, WINED3DTS_WORLDMATRIX(244) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(244)), transform_worldex },
3749 { /*501, WINED3DTS_WORLDMATRIX(245) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(245)), transform_worldex },
3750 { /*502, WINED3DTS_WORLDMATRIX(246) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(246)), transform_worldex },
3751 { /*503, WINED3DTS_WORLDMATRIX(247) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(247)), transform_worldex },
3752 { /*504, WINED3DTS_WORLDMATRIX(248) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(248)), transform_worldex },
3753 { /*505, WINED3DTS_WORLDMATRIX(249) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(249)), transform_worldex },
3754 { /*506, WINED3DTS_WORLDMATRIX(250) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(250)), transform_worldex },
3755 { /*507, WINED3DTS_WORLDMATRIX(251) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(251)), transform_worldex },
3756 { /*508, WINED3DTS_WORLDMATRIX(252) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(252)), transform_worldex },
3757 { /*509, WINED3DTS_WORLDMATRIX(253) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(253)), transform_worldex },
3758 { /*510, WINED3DTS_WORLDMATRIX(254) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(254)), transform_worldex },
3759 { /*511, WINED3DTS_WORLDMATRIX(255) */ STATE_TRANSFORM(WINED3DTS_WORLDMATRIX(255)), transform_worldex },
3760 /* Various Vertex states follow */
3761 { /* , STATE_STREAMSRC */ STATE_VDECL, vertexdeclaration },
3762 { /* , STATE_VDECL */ STATE_VDECL, vertexdeclaration },
3763 { /* , STATE_VSHADER */ STATE_VDECL, vertexdeclaration },
3764 { /* , STATE_VIEWPORT */ STATE_VIEWPORT, viewport },
3765 { /* , STATE_VERTEXSHADERCONSTANT */ STATE_VERTEXSHADERCONSTANT, shaderconstant },
3766 { /* , STATE_PIXELSHADERCONSTANT */ STATE_VERTEXSHADERCONSTANT, shaderconstant },