2 * Direct3D state management
4 * Copyright 2002 Lionel Ulmer
5 * Copyright 2002-2005 Jason Edmeades
6 * Copyright 2003-2004 Raphael Junqueira
7 * Copyright 2004 Christian Costa
8 * Copyright 2005 Oliver Stieber
9 * Copyright 2006 Henri Verbeet
10 * Copyright 2006-2008 Stefan Dösinger for CodeWeavers
11 * Copyright 2009-2011 Henri Verbeet for CodeWeavers
13 * This library is free software; you can redistribute it and/or
14 * modify it under the terms of the GNU Lesser General Public
15 * License as published by the Free Software Foundation; either
16 * version 2.1 of the License, or (at your option) any later version.
18 * This library is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21 * Lesser General Public License for more details.
23 * You should have received a copy of the GNU Lesser General Public
24 * License along with this library; if not, write to the Free Software
25 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
29 #include "wine/port.h"
36 #include "wined3d_private.h"
38 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
39 WINE_DECLARE_DEBUG_CHANNEL(d3d_shader);
41 /* GL locking for state handlers is done by the caller. */
43 static void state_undefined(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
45 ERR("Undefined state.\n");
48 static void state_nop(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
50 TRACE("%s: nop in current pipe config.\n", debug_d3dstate(state_id));
53 static void state_fillmode(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
55 enum wined3d_fill_mode mode = state->render_states[WINED3D_RS_FILLMODE];
56 const struct wined3d_gl_info *gl_info = context->gl_info;
60 case WINED3D_FILL_POINT:
61 gl_info->gl_ops.gl.p_glPolygonMode(GL_FRONT_AND_BACK, GL_POINT);
62 checkGLcall("glPolygonMode(GL_FRONT_AND_BACK, GL_POINT)");
64 case WINED3D_FILL_WIREFRAME:
65 gl_info->gl_ops.gl.p_glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
66 checkGLcall("glPolygonMode(GL_FRONT_AND_BACK, GL_LINE)");
68 case WINED3D_FILL_SOLID:
69 gl_info->gl_ops.gl.p_glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
70 checkGLcall("glPolygonMode(GL_FRONT_AND_BACK, GL_FILL)");
73 FIXME("Unrecognized fill mode %#x.\n", mode);
77 static void state_lighting(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
79 const struct wined3d_gl_info *gl_info = context->gl_info;
81 /* Lighting is not enabled if transformed vertices are drawn, but lighting
82 * does not affect the stream sources, so it is not grouped for
83 * performance reasons. This state reads the decoded vertex declaration,
84 * so if it is dirty don't do anything. The vertex declaration applying
85 * function calls this function for updating. */
86 if (isStateDirty(context, STATE_VDECL))
89 if (state->render_states[WINED3D_RS_LIGHTING]
90 && !context->swapchain->device->strided_streams.position_transformed)
92 gl_info->gl_ops.gl.p_glEnable(GL_LIGHTING);
93 checkGLcall("glEnable GL_LIGHTING");
97 gl_info->gl_ops.gl.p_glDisable(GL_LIGHTING);
98 checkGLcall("glDisable GL_LIGHTING");
102 static void state_zenable(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
104 enum wined3d_depth_buffer_type zenable = state->render_states[WINED3D_RS_ZENABLE];
105 const struct wined3d_gl_info *gl_info = context->gl_info;
108 /* No z test without depth stencil buffers */
109 if (!state->fb->depth_stencil)
111 TRACE("No Z buffer - disabling depth test\n");
112 zenable = WINED3D_ZB_FALSE;
117 case WINED3D_ZB_FALSE:
118 gl_info->gl_ops.gl.p_glDisable(GL_DEPTH_TEST);
119 checkGLcall("glDisable GL_DEPTH_TEST");
121 case WINED3D_ZB_TRUE:
122 gl_info->gl_ops.gl.p_glEnable(GL_DEPTH_TEST);
123 checkGLcall("glEnable GL_DEPTH_TEST");
125 case WINED3D_ZB_USEW:
126 gl_info->gl_ops.gl.p_glEnable(GL_DEPTH_TEST);
127 checkGLcall("glEnable GL_DEPTH_TEST");
128 FIXME("W buffer is not well handled\n");
131 FIXME("Unrecognized depth buffer type %#x.\n", zenable);
135 if (context->gl_info->supported[ARB_DEPTH_CLAMP])
137 if (!zenable && context->swapchain->device->strided_streams.position_transformed)
139 gl_info->gl_ops.gl.p_glEnable(GL_DEPTH_CLAMP);
140 checkGLcall("glEnable(GL_DEPTH_CLAMP)");
144 gl_info->gl_ops.gl.p_glDisable(GL_DEPTH_CLAMP);
145 checkGLcall("glDisable(GL_DEPTH_CLAMP)");
148 else if (!zenable && !once++)
149 FIXME("Z buffer disabled, but ARB_depth_clamp isn't supported.\n");
152 static void state_cullmode(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
154 const struct wined3d_gl_info *gl_info = context->gl_info;
156 /* glFrontFace() is set in context.c at context init and on an
157 * offscreen / onscreen rendering switch. */
158 switch (state->render_states[WINED3D_RS_CULLMODE])
160 case WINED3D_CULL_NONE:
161 gl_info->gl_ops.gl.p_glDisable(GL_CULL_FACE);
162 checkGLcall("glDisable GL_CULL_FACE");
164 case WINED3D_CULL_CW:
165 gl_info->gl_ops.gl.p_glEnable(GL_CULL_FACE);
166 checkGLcall("glEnable GL_CULL_FACE");
167 gl_info->gl_ops.gl.p_glCullFace(GL_FRONT);
168 checkGLcall("glCullFace(GL_FRONT)");
170 case WINED3D_CULL_CCW:
171 gl_info->gl_ops.gl.p_glEnable(GL_CULL_FACE);
172 checkGLcall("glEnable GL_CULL_FACE");
173 gl_info->gl_ops.gl.p_glCullFace(GL_BACK);
174 checkGLcall("glCullFace(GL_BACK)");
177 FIXME("Unrecognized cull mode %#x.\n",
178 state->render_states[WINED3D_RS_CULLMODE]);
182 static void state_shademode(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
184 const struct wined3d_gl_info *gl_info = context->gl_info;
186 switch (state->render_states[WINED3D_RS_SHADEMODE])
188 case WINED3D_SHADE_FLAT:
189 gl_info->gl_ops.gl.p_glShadeModel(GL_FLAT);
190 checkGLcall("glShadeModel(GL_FLAT)");
192 case WINED3D_SHADE_GOURAUD:
193 gl_info->gl_ops.gl.p_glShadeModel(GL_SMOOTH);
194 checkGLcall("glShadeModel(GL_SMOOTH)");
196 case WINED3D_SHADE_PHONG:
197 FIXME("WINED3D_SHADE_PHONG isn't supported.\n");
200 FIXME("Unrecognized shade mode %#x.\n",
201 state->render_states[WINED3D_RS_SHADEMODE]);
205 static void state_ditherenable(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
207 const struct wined3d_gl_info *gl_info = context->gl_info;
209 if (state->render_states[WINED3D_RS_DITHERENABLE])
211 gl_info->gl_ops.gl.p_glEnable(GL_DITHER);
212 checkGLcall("glEnable GL_DITHER");
216 gl_info->gl_ops.gl.p_glDisable(GL_DITHER);
217 checkGLcall("glDisable GL_DITHER");
221 static void state_zwritenable(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
223 const struct wined3d_gl_info *gl_info = context->gl_info;
225 if (state->render_states[WINED3D_RS_ZWRITEENABLE])
227 gl_info->gl_ops.gl.p_glDepthMask(1);
228 checkGLcall("glDepthMask(1)");
232 gl_info->gl_ops.gl.p_glDepthMask(0);
233 checkGLcall("glDepthMask(0)");
237 static GLenum gl_compare_func(enum wined3d_cmp_func f)
241 case WINED3D_CMP_NEVER:
243 case WINED3D_CMP_LESS:
245 case WINED3D_CMP_EQUAL:
247 case WINED3D_CMP_LESSEQUAL:
249 case WINED3D_CMP_GREATER:
251 case WINED3D_CMP_NOTEQUAL:
253 case WINED3D_CMP_GREATEREQUAL:
255 case WINED3D_CMP_ALWAYS:
258 FIXME("Unrecognized compare function %#x.\n", f);
263 static void state_zfunc(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
265 GLenum depth_func = gl_compare_func(state->render_states[WINED3D_RS_ZFUNC]);
266 const struct wined3d_gl_info *gl_info = context->gl_info;
268 if (!depth_func) return;
270 if (depth_func == GL_EQUAL || depth_func == GL_NOTEQUAL)
273 /* There are a few issues with this: First, our inability to
274 * select a proper Z depth, most of the time we're stuck with
275 * D24S8, even if the app selects D32 or D16. There seem to be
276 * some other precision problems which have to be debugged to
277 * make NOTEQUAL and EQUAL work properly. */
281 FIXME("D3DCMP_NOTEQUAL and D3DCMP_EQUAL do not work correctly yet.\n");
285 gl_info->gl_ops.gl.p_glDepthFunc(depth_func);
286 checkGLcall("glDepthFunc");
289 static void state_ambient(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
291 const struct wined3d_gl_info *gl_info = context->gl_info;
294 D3DCOLORTOGLFLOAT4(state->render_states[WINED3D_RS_AMBIENT], col);
295 TRACE("Setting ambient to (%f,%f,%f,%f)\n", col[0], col[1], col[2], col[3]);
296 gl_info->gl_ops.gl.p_glLightModelfv(GL_LIGHT_MODEL_AMBIENT, col);
297 checkGLcall("glLightModel for MODEL_AMBIENT");
300 static void state_blendop_w(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
302 WARN("Unsupported in local OpenGL implementation: glBlendEquation\n");
305 static GLenum gl_blend_op(enum wined3d_blend_op op)
309 case WINED3D_BLEND_OP_ADD:
310 return GL_FUNC_ADD_EXT;
311 case WINED3D_BLEND_OP_SUBTRACT:
312 return GL_FUNC_SUBTRACT_EXT;
313 case WINED3D_BLEND_OP_REVSUBTRACT:
314 return GL_FUNC_REVERSE_SUBTRACT_EXT;
315 case WINED3D_BLEND_OP_MIN:
317 case WINED3D_BLEND_OP_MAX:
320 FIXME("Unhandled blend op %#x.\n", op);
325 static void state_blendop(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
327 const struct wined3d_gl_info *gl_info = context->gl_info;
328 GLenum blend_equation_alpha = GL_FUNC_ADD_EXT;
329 GLenum blend_equation = GL_FUNC_ADD_EXT;
331 /* BLENDOPALPHA requires GL_EXT_blend_equation_separate, so make sure it is around */
332 if (state->render_states[WINED3D_RS_BLENDOPALPHA]
333 && !gl_info->supported[EXT_BLEND_EQUATION_SEPARATE])
335 WARN("Unsupported in local OpenGL implementation: glBlendEquationSeparateEXT\n");
339 blend_equation = gl_blend_op(state->render_states[WINED3D_RS_BLENDOP]);
340 blend_equation_alpha = gl_blend_op(state->render_states[WINED3D_RS_BLENDOPALPHA]);
341 TRACE("blend_equation %#x, blend_equation_alpha %#x.\n", blend_equation, blend_equation_alpha);
343 if (state->render_states[WINED3D_RS_SEPARATEALPHABLENDENABLE])
345 GL_EXTCALL(glBlendEquationSeparateEXT(blend_equation, blend_equation_alpha));
346 checkGLcall("glBlendEquationSeparateEXT");
350 GL_EXTCALL(glBlendEquationEXT(blend_equation));
351 checkGLcall("glBlendEquation");
355 static GLenum gl_blend_factor(enum wined3d_blend factor, const struct wined3d_format *dst_format)
359 case WINED3D_BLEND_ZERO:
361 case WINED3D_BLEND_ONE:
363 case WINED3D_BLEND_SRCCOLOR:
365 case WINED3D_BLEND_INVSRCCOLOR:
366 return GL_ONE_MINUS_SRC_COLOR;
367 case WINED3D_BLEND_SRCALPHA:
369 case WINED3D_BLEND_INVSRCALPHA:
370 return GL_ONE_MINUS_SRC_ALPHA;
371 case WINED3D_BLEND_DESTCOLOR:
373 case WINED3D_BLEND_INVDESTCOLOR:
374 return GL_ONE_MINUS_DST_COLOR;
375 /* To compensate for the lack of format switching with backbuffer
376 * offscreen rendering, and with onscreen rendering, we modify the
377 * alpha test parameters for (INV)DESTALPHA if the render target
378 * doesn't support alpha blending. A nonexistent alpha channel
379 * returns 1.0, so WINED3D_BLEND_DESTALPHA becomes GL_ONE, and
380 * WINED3D_BLEND_INVDESTALPHA becomes GL_ZERO. */
381 case WINED3D_BLEND_DESTALPHA:
382 return dst_format->alpha_size ? GL_DST_ALPHA : GL_ONE;
383 case WINED3D_BLEND_INVDESTALPHA:
384 return dst_format->alpha_size ? GL_ONE_MINUS_DST_ALPHA : GL_ZERO;
385 case WINED3D_BLEND_SRCALPHASAT:
386 return GL_SRC_ALPHA_SATURATE;
387 case WINED3D_BLEND_BLENDFACTOR:
388 return GL_CONSTANT_COLOR_EXT;
389 case WINED3D_BLEND_INVBLENDFACTOR:
390 return GL_ONE_MINUS_CONSTANT_COLOR_EXT;
392 FIXME("Unhandled blend factor %#x.\n", factor);
397 static void state_blend(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
399 const struct wined3d_surface *target = state->fb->render_targets[0];
400 const struct wined3d_gl_info *gl_info = context->gl_info;
401 GLenum srcBlend, dstBlend;
402 enum wined3d_blend d3d_blend;
404 /* According to the red book, GL_LINE_SMOOTH needs GL_BLEND with specific
405 * blending parameters to work. */
406 if (state->render_states[WINED3D_RS_ALPHABLENDENABLE]
407 || state->render_states[WINED3D_RS_EDGEANTIALIAS]
408 || state->render_states[WINED3D_RS_ANTIALIASEDLINEENABLE])
410 /* Disable blending in all cases even without pixelshaders.
411 * With blending on we could face a big performance penalty.
412 * The d3d9 visual test confirms the behavior. */
413 if (context->render_offscreen
414 && !(target->resource.format->flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING))
416 gl_info->gl_ops.gl.p_glDisable(GL_BLEND);
417 checkGLcall("glDisable GL_BLEND");
422 gl_info->gl_ops.gl.p_glEnable(GL_BLEND);
423 checkGLcall("glEnable GL_BLEND");
428 gl_info->gl_ops.gl.p_glDisable(GL_BLEND);
429 checkGLcall("glDisable GL_BLEND");
430 /* Nothing more to do - get out */
434 /* WINED3D_BLEND_BOTHSRCALPHA and WINED3D_BLEND_BOTHINVSRCALPHA are legacy
435 * source blending values which are still valid up to d3d9. They should
436 * not occur as dest blend values. */
437 d3d_blend = state->render_states[WINED3D_RS_SRCBLEND];
438 if (d3d_blend == WINED3D_BLEND_BOTHSRCALPHA)
440 srcBlend = GL_SRC_ALPHA;
441 dstBlend = GL_ONE_MINUS_SRC_ALPHA;
443 else if (d3d_blend == WINED3D_BLEND_BOTHINVSRCALPHA)
445 srcBlend = GL_ONE_MINUS_SRC_ALPHA;
446 dstBlend = GL_SRC_ALPHA;
450 srcBlend = gl_blend_factor(d3d_blend, target->resource.format);
451 dstBlend = gl_blend_factor(state->render_states[WINED3D_RS_DESTBLEND],
452 target->resource.format);
455 if (state->render_states[WINED3D_RS_EDGEANTIALIAS]
456 || state->render_states[WINED3D_RS_ANTIALIASEDLINEENABLE])
458 gl_info->gl_ops.gl.p_glEnable(GL_LINE_SMOOTH);
459 checkGLcall("glEnable(GL_LINE_SMOOTH)");
460 if (srcBlend != GL_SRC_ALPHA)
461 WARN("WINED3D_RS_EDGEANTIALIAS enabled, but unexpected src blending param.\n");
462 if (dstBlend != GL_ONE_MINUS_SRC_ALPHA && dstBlend != GL_ONE)
463 WARN("WINED3D_RS_EDGEANTIALIAS enabled, but unexpected dst blending param.\n");
467 gl_info->gl_ops.gl.p_glDisable(GL_LINE_SMOOTH);
468 checkGLcall("glDisable(GL_LINE_SMOOTH)");
471 /* Re-apply BLENDOP(ALPHA) because of a possible SEPARATEALPHABLENDENABLE change */
472 if (!isStateDirty(context, STATE_RENDER(WINED3D_RS_BLENDOP)))
473 state_blendop(context, state, STATE_RENDER(WINED3D_RS_BLENDOPALPHA));
475 if (state->render_states[WINED3D_RS_SEPARATEALPHABLENDENABLE])
477 GLenum srcBlendAlpha, dstBlendAlpha;
479 /* Separate alpha blending requires GL_EXT_blend_function_separate, so make sure it is around */
480 if (!context->gl_info->supported[EXT_BLEND_FUNC_SEPARATE])
482 WARN("Unsupported in local OpenGL implementation: glBlendFuncSeparateEXT\n");
486 /* WINED3D_BLEND_BOTHSRCALPHA and WINED3D_BLEND_BOTHINVSRCALPHA are legacy
487 * source blending values which are still valid up to d3d9. They should
488 * not occur as dest blend values. */
489 d3d_blend = state->render_states[WINED3D_RS_SRCBLENDALPHA];
490 if (d3d_blend == WINED3D_BLEND_BOTHSRCALPHA)
492 srcBlendAlpha = GL_SRC_ALPHA;
493 dstBlendAlpha = GL_ONE_MINUS_SRC_ALPHA;
495 else if (d3d_blend == WINED3D_BLEND_BOTHINVSRCALPHA)
497 srcBlendAlpha = GL_ONE_MINUS_SRC_ALPHA;
498 dstBlendAlpha = GL_SRC_ALPHA;
502 srcBlendAlpha = gl_blend_factor(d3d_blend, target->resource.format);
503 dstBlendAlpha = gl_blend_factor(state->render_states[WINED3D_RS_DESTBLENDALPHA],
504 target->resource.format);
507 GL_EXTCALL(glBlendFuncSeparateEXT(srcBlend, dstBlend, srcBlendAlpha, dstBlendAlpha));
508 checkGLcall("glBlendFuncSeparateEXT");
512 TRACE("glBlendFunc src=%x, dst=%x\n", srcBlend, dstBlend);
513 gl_info->gl_ops.gl.p_glBlendFunc(srcBlend, dstBlend);
514 checkGLcall("glBlendFunc");
517 /* Colorkey fixup for stage 0 alphaop depends on
518 * WINED3D_RS_ALPHABLENDENABLE state, so it may need updating. */
519 if (state->render_states[WINED3D_RS_COLORKEYENABLE])
520 context_apply_state(context, state, STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_OP));
523 static void state_blendfactor_w(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
525 WARN("Unsupported in local OpenGL implementation: glBlendColorEXT\n");
528 static void state_blendfactor(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
530 const struct wined3d_gl_info *gl_info = context->gl_info;
533 TRACE("Setting blend factor to %#x.\n", state->render_states[WINED3D_RS_BLENDFACTOR]);
535 D3DCOLORTOGLFLOAT4(state->render_states[WINED3D_RS_BLENDFACTOR], col);
536 GL_EXTCALL(glBlendColorEXT (col[0],col[1],col[2],col[3]));
537 checkGLcall("glBlendColor");
540 static void state_alpha(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
542 const struct wined3d_gl_info *gl_info = context->gl_info;
545 BOOL enable_ckey = FALSE;
547 TRACE("context %p, state %p, state_id %#x.\n", context, state, state_id);
549 /* Find out if the texture on the first stage has a ckey set
550 * The alpha state func reads the texture settings, even though alpha and texture are not grouped
551 * together. This is to avoid making a huge alpha+texture+texture stage+ckey block due to the hardly
552 * used WINED3D_RS_COLORKEYENABLE state(which is d3d <= 3 only). The texture function will call alpha
553 * in case it finds some texture+colorkeyenable combination which needs extra care.
555 if (state->textures[0])
557 struct wined3d_surface *surface = surface_from_resource(state->textures[0]->sub_resources[0]);
559 if (surface->CKeyFlags & WINEDDSD_CKSRCBLT)
563 if (enable_ckey || context->last_was_ckey)
564 context_apply_state(context, state, STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_OP));
565 context->last_was_ckey = enable_ckey;
567 if (state->render_states[WINED3D_RS_ALPHATESTENABLE]
568 || (state->render_states[WINED3D_RS_COLORKEYENABLE] && enable_ckey))
570 gl_info->gl_ops.gl.p_glEnable(GL_ALPHA_TEST);
571 checkGLcall("glEnable GL_ALPHA_TEST");
575 gl_info->gl_ops.gl.p_glDisable(GL_ALPHA_TEST);
576 checkGLcall("glDisable GL_ALPHA_TEST");
577 /* Alpha test is disabled, don't bother setting the params - it will happen on the next
583 if (state->render_states[WINED3D_RS_COLORKEYENABLE] && enable_ckey)
585 glParm = GL_NOTEQUAL;
590 ref = ((float)state->render_states[WINED3D_RS_ALPHAREF]) / 255.0f;
591 glParm = gl_compare_func(state->render_states[WINED3D_RS_ALPHAFUNC]);
595 gl_info->gl_ops.gl.p_glAlphaFunc(glParm, ref);
596 checkGLcall("glAlphaFunc");
600 static void shaderconstant(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
602 context->load_constants = 1;
605 static void state_clipping(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
607 const struct wined3d_gl_info *gl_info = context->gl_info;
608 DWORD enable = 0xffffffff;
609 DWORD disable = 0x00000000;
613 const struct wined3d_device *device = context->swapchain->device;
615 if (!device->vs_clipping)
617 /* The spec says that opengl clipping planes are disabled when using shaders. Direct3D planes aren't,
618 * so that is an issue. The MacOS ATI driver keeps clipping planes activated with shaders in some
619 * conditions I got sick of tracking down. The shader state handler disables all clip planes because
620 * of that - don't do anything here and keep them disabled
622 if (state->render_states[WINED3D_RS_CLIPPLANEENABLE])
624 static BOOL warned = FALSE;
626 FIXME("Clipping not supported with vertex shaders\n");
633 /* glEnable(GL_CLIP_PLANEx) doesn't apply to vertex shaders. The enabled / disabled planes are
634 * hardcoded into the shader. Update the shader to update the enabled clipplanes */
635 context->select_shader = 1;
636 context->load_constants = 1;
639 /* TODO: Keep track of previously enabled clipplanes to avoid unnecessary resetting
640 * of already set values
643 /* If enabling / disabling all
644 * TODO: Is this correct? Doesn't D3DRS_CLIPPING disable clipping on the viewport frustrum?
646 if (state->render_states[WINED3D_RS_CLIPPING])
648 enable = state->render_states[WINED3D_RS_CLIPPLANEENABLE];
649 disable = ~state->render_states[WINED3D_RS_CLIPPLANEENABLE];
653 disable = 0xffffffff;
657 if (enable & WINED3DCLIPPLANE0) gl_info->gl_ops.gl.p_glEnable(GL_CLIP_PLANE0);
658 if (enable & WINED3DCLIPPLANE1) gl_info->gl_ops.gl.p_glEnable(GL_CLIP_PLANE1);
659 if (enable & WINED3DCLIPPLANE2) gl_info->gl_ops.gl.p_glEnable(GL_CLIP_PLANE2);
660 if (enable & WINED3DCLIPPLANE3) gl_info->gl_ops.gl.p_glEnable(GL_CLIP_PLANE3);
661 if (enable & WINED3DCLIPPLANE4) gl_info->gl_ops.gl.p_glEnable(GL_CLIP_PLANE4);
662 if (enable & WINED3DCLIPPLANE5) gl_info->gl_ops.gl.p_glEnable(GL_CLIP_PLANE5);
663 checkGLcall("clip plane enable");
665 if (disable & WINED3DCLIPPLANE0) gl_info->gl_ops.gl.p_glDisable(GL_CLIP_PLANE0);
666 if (disable & WINED3DCLIPPLANE1) gl_info->gl_ops.gl.p_glDisable(GL_CLIP_PLANE1);
667 if (disable & WINED3DCLIPPLANE2) gl_info->gl_ops.gl.p_glDisable(GL_CLIP_PLANE2);
668 if (disable & WINED3DCLIPPLANE3) gl_info->gl_ops.gl.p_glDisable(GL_CLIP_PLANE3);
669 if (disable & WINED3DCLIPPLANE4) gl_info->gl_ops.gl.p_glDisable(GL_CLIP_PLANE4);
670 if (disable & WINED3DCLIPPLANE5) gl_info->gl_ops.gl.p_glDisable(GL_CLIP_PLANE5);
671 checkGLcall("clip plane disable");
674 static void state_specularenable(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
676 const struct wined3d_gl_info *gl_info = context->gl_info;
677 /* Originally this used glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL,GL_SEPARATE_SPECULAR_COLOR)
678 * and (GL_LIGHT_MODEL_COLOR_CONTROL,GL_SINGLE_COLOR) to swap between enabled/disabled
679 * specular color. This is wrong:
680 * Separate specular color means the specular colour is maintained separately, whereas
681 * single color means it is merged in. However in both cases they are being used to
683 * To disable specular color, set it explicitly to black and turn off GL_COLOR_SUM_EXT
684 * NOTE: If not supported don't give FIXMEs the impact is really minimal and very few people are
688 * If register combiners are enabled, enabling / disabling GL_COLOR_SUM has no effect.
689 * Instead, we need to setup the FinalCombiner properly.
691 * The default setup for the FinalCombiner is:
693 * <variable> <input> <mapping> <usage>
694 * GL_VARIABLE_A_NV GL_FOG, GL_UNSIGNED_IDENTITY_NV GL_ALPHA
695 * GL_VARIABLE_B_NV GL_SPARE0_PLUS_SECONDARY_COLOR_NV GL_UNSIGNED_IDENTITY_NV GL_RGB
696 * GL_VARIABLE_C_NV GL_FOG GL_UNSIGNED_IDENTITY_NV GL_RGB
697 * GL_VARIABLE_D_NV GL_ZERO GL_UNSIGNED_IDENTITY_NV GL_RGB
698 * GL_VARIABLE_E_NV GL_ZERO GL_UNSIGNED_IDENTITY_NV GL_RGB
699 * GL_VARIABLE_F_NV GL_ZERO GL_UNSIGNED_IDENTITY_NV GL_RGB
700 * GL_VARIABLE_G_NV GL_SPARE0_NV GL_UNSIGNED_IDENTITY_NV GL_ALPHA
702 * That's pretty much fine as it is, except for variable B, which needs to take
703 * either GL_SPARE0_PLUS_SECONDARY_COLOR_NV or GL_SPARE0_NV, depending on
704 * whether WINED3D_RS_SPECULARENABLE is enabled or not.
707 TRACE("Setting specular enable state and materials\n");
708 if (state->render_states[WINED3D_RS_SPECULARENABLE])
710 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, (float *)&state->material.specular);
711 checkGLcall("glMaterialfv");
713 if (state->material.power > gl_info->limits.shininess)
715 /* glMaterialf man page says that the material says that GL_SHININESS must be between 0.0
716 * and 128.0, although in d3d neither -1 nor 129 produce an error. GL_NV_max_light_exponent
717 * allows bigger values. If the extension is supported, gl_info->limits.shininess contains the
718 * value reported by the extension, otherwise 128. For values > gl_info->limits.shininess clamp
719 * them, it should be safe to do so without major visual distortions.
721 WARN("Material power = %.8e, limit %.8e\n", state->material.power, gl_info->limits.shininess);
722 gl_info->gl_ops.gl.p_glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, gl_info->limits.shininess);
726 gl_info->gl_ops.gl.p_glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, state->material.power);
728 checkGLcall("glMaterialf(GL_SHININESS)");
730 if (gl_info->supported[EXT_SECONDARY_COLOR])
731 gl_info->gl_ops.gl.p_glEnable(GL_COLOR_SUM_EXT);
733 TRACE("Specular colors cannot be enabled in this version of opengl\n");
734 checkGLcall("glEnable(GL_COLOR_SUM)");
736 if (gl_info->supported[NV_REGISTER_COMBINERS])
738 GL_EXTCALL(glFinalCombinerInputNV(GL_VARIABLE_B_NV, GL_SPARE0_PLUS_SECONDARY_COLOR_NV, GL_UNSIGNED_IDENTITY_NV, GL_RGB));
739 checkGLcall("glFinalCombinerInputNV()");
742 static const GLfloat black[] = {0.0f, 0.0f, 0.0f, 0.0f};
744 /* for the case of enabled lighting: */
745 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, &black[0]);
746 checkGLcall("glMaterialfv");
748 /* for the case of disabled lighting: */
749 if (gl_info->supported[EXT_SECONDARY_COLOR])
750 gl_info->gl_ops.gl.p_glDisable(GL_COLOR_SUM_EXT);
752 TRACE("Specular colors cannot be disabled in this version of opengl\n");
753 checkGLcall("glDisable(GL_COLOR_SUM)");
755 if (gl_info->supported[NV_REGISTER_COMBINERS])
757 GL_EXTCALL(glFinalCombinerInputNV(GL_VARIABLE_B_NV, GL_SPARE0_NV, GL_UNSIGNED_IDENTITY_NV, GL_RGB));
758 checkGLcall("glFinalCombinerInputNV()");
762 TRACE("diffuse {%.8e, %.8e, %.8e, %.8e}\n",
763 state->material.diffuse.r, state->material.diffuse.g,
764 state->material.diffuse.b, state->material.diffuse.a);
765 TRACE("ambient {%.8e, %.8e, %.8e, %.8e}\n",
766 state->material.ambient.r, state->material.ambient.g,
767 state->material.ambient.b, state->material.ambient.a);
768 TRACE("specular {%.8e, %.8e, %.8e, %.8e}\n",
769 state->material.specular.r, state->material.specular.g,
770 state->material.specular.b, state->material.specular.a);
771 TRACE("emissive {%.8e, %.8e, %.8e, %.8e}\n",
772 state->material.emissive.r, state->material.emissive.g,
773 state->material.emissive.b, state->material.emissive.a);
775 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float *)&state->material.ambient);
776 checkGLcall("glMaterialfv(GL_AMBIENT)");
777 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float *)&state->material.diffuse);
778 checkGLcall("glMaterialfv(GL_DIFFUSE)");
779 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, (float *)&state->material.emissive);
780 checkGLcall("glMaterialfv(GL_EMISSION)");
783 static void state_texfactor(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
785 const struct wined3d_gl_info *gl_info = context->gl_info;
788 /* Note the texture color applies to all textures whereas
789 * GL_TEXTURE_ENV_COLOR applies to active only. */
791 D3DCOLORTOGLFLOAT4(state->render_states[WINED3D_RS_TEXTUREFACTOR], col);
793 /* And now the default texture color as well */
794 for (i = 0; i < gl_info->limits.texture_stages; ++i)
796 /* Note the WINED3D_RS value applies to all textures, but GL has one
797 * per texture, so apply it now ready to be used! */
798 context_active_texture(context, gl_info, i);
800 gl_info->gl_ops.gl.p_glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, &col[0]);
801 checkGLcall("glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, color);");
805 static void renderstate_stencil_twosided(struct wined3d_context *context, GLint face,
806 GLint func, GLint ref, GLuint mask, GLint stencilFail, GLint depthFail, GLint stencilPass)
808 const struct wined3d_gl_info *gl_info = context->gl_info;
810 gl_info->gl_ops.gl.p_glEnable(GL_STENCIL_TEST_TWO_SIDE_EXT);
811 checkGLcall("glEnable(GL_STENCIL_TEST_TWO_SIDE_EXT)");
812 GL_EXTCALL(glActiveStencilFaceEXT(face));
813 checkGLcall("glActiveStencilFaceEXT(...)");
814 gl_info->gl_ops.gl.p_glStencilFunc(func, ref, mask);
815 checkGLcall("glStencilFunc(...)");
816 gl_info->gl_ops.gl.p_glStencilOp(stencilFail, depthFail, stencilPass);
817 checkGLcall("glStencilOp(...)");
820 static GLenum gl_stencil_op(enum wined3d_stencil_op op)
824 case WINED3D_STENCIL_OP_KEEP:
826 case WINED3D_STENCIL_OP_ZERO:
828 case WINED3D_STENCIL_OP_REPLACE:
830 case WINED3D_STENCIL_OP_INCR_SAT:
832 case WINED3D_STENCIL_OP_DECR_SAT:
834 case WINED3D_STENCIL_OP_INVERT:
836 case WINED3D_STENCIL_OP_INCR:
837 return GL_INCR_WRAP_EXT;
838 case WINED3D_STENCIL_OP_DECR:
839 return GL_DECR_WRAP_EXT;
841 FIXME("Unrecognized stencil op %#x.\n", op);
846 static void state_stencil(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
848 const struct wined3d_gl_info *gl_info = context->gl_info;
849 DWORD onesided_enable = FALSE;
850 DWORD twosided_enable = FALSE;
851 GLint func = GL_ALWAYS;
852 GLint func_ccw = GL_ALWAYS;
855 GLint stencilFail = GL_KEEP;
856 GLint depthFail = GL_KEEP;
857 GLint stencilPass = GL_KEEP;
858 GLint stencilFail_ccw = GL_KEEP;
859 GLint depthFail_ccw = GL_KEEP;
860 GLint stencilPass_ccw = GL_KEEP;
862 /* No stencil test without a stencil buffer. */
863 if (!state->fb->depth_stencil)
865 gl_info->gl_ops.gl.p_glDisable(GL_STENCIL_TEST);
866 checkGLcall("glDisable GL_STENCIL_TEST");
870 onesided_enable = state->render_states[WINED3D_RS_STENCILENABLE];
871 twosided_enable = state->render_states[WINED3D_RS_TWOSIDEDSTENCILMODE];
872 if (!(func = gl_compare_func(state->render_states[WINED3D_RS_STENCILFUNC])))
874 if (!(func_ccw = gl_compare_func(state->render_states[WINED3D_RS_CCW_STENCILFUNC])))
875 func_ccw = GL_ALWAYS;
876 ref = state->render_states[WINED3D_RS_STENCILREF];
877 mask = state->render_states[WINED3D_RS_STENCILMASK];
878 stencilFail = gl_stencil_op(state->render_states[WINED3D_RS_STENCILFAIL]);
879 depthFail = gl_stencil_op(state->render_states[WINED3D_RS_STENCILZFAIL]);
880 stencilPass = gl_stencil_op(state->render_states[WINED3D_RS_STENCILPASS]);
881 stencilFail_ccw = gl_stencil_op(state->render_states[WINED3D_RS_CCW_STENCILFAIL]);
882 depthFail_ccw = gl_stencil_op(state->render_states[WINED3D_RS_CCW_STENCILZFAIL]);
883 stencilPass_ccw = gl_stencil_op(state->render_states[WINED3D_RS_CCW_STENCILPASS]);
885 TRACE("(onesided %d, twosided %d, ref %x, mask %x, "
886 "GL_FRONT: func: %x, fail %x, zfail %x, zpass %x "
887 "GL_BACK: func: %x, fail %x, zfail %x, zpass %x )\n",
888 onesided_enable, twosided_enable, ref, mask,
889 func, stencilFail, depthFail, stencilPass,
890 func_ccw, stencilFail_ccw, depthFail_ccw, stencilPass_ccw);
892 if (twosided_enable && onesided_enable)
894 gl_info->gl_ops.gl.p_glEnable(GL_STENCIL_TEST);
895 checkGLcall("glEnable GL_STENCIL_TEST");
897 if (gl_info->supported[EXT_STENCIL_TWO_SIDE])
899 /* Apply back first, then front. This function calls glActiveStencilFaceEXT,
900 * which has an effect on the code below too. If we apply the front face
901 * afterwards, we are sure that the active stencil face is set to front,
902 * and other stencil functions which do not use two sided stencil do not have
905 renderstate_stencil_twosided(context, GL_BACK,
906 func_ccw, ref, mask, stencilFail_ccw, depthFail_ccw, stencilPass_ccw);
907 renderstate_stencil_twosided(context, GL_FRONT,
908 func, ref, mask, stencilFail, depthFail, stencilPass);
910 else if (gl_info->supported[ATI_SEPARATE_STENCIL])
912 GL_EXTCALL(glStencilFuncSeparateATI(func, func_ccw, ref, mask));
913 checkGLcall("glStencilFuncSeparateATI(...)");
914 GL_EXTCALL(glStencilOpSeparateATI(GL_FRONT, stencilFail, depthFail, stencilPass));
915 checkGLcall("glStencilOpSeparateATI(GL_FRONT, ...)");
916 GL_EXTCALL(glStencilOpSeparateATI(GL_BACK, stencilFail_ccw, depthFail_ccw, stencilPass_ccw));
917 checkGLcall("glStencilOpSeparateATI(GL_BACK, ...)");
919 ERR("Separate (two sided) stencil not supported on this version of opengl. Caps weren't honored?\n");
922 else if(onesided_enable)
924 if (gl_info->supported[EXT_STENCIL_TWO_SIDE])
926 gl_info->gl_ops.gl.p_glDisable(GL_STENCIL_TEST_TWO_SIDE_EXT);
927 checkGLcall("glDisable(GL_STENCIL_TEST_TWO_SIDE_EXT)");
930 /* This code disables the ATI extension as well, since the standard stencil functions are equal
931 * to calling the ATI functions with GL_FRONT_AND_BACK as face parameter
933 gl_info->gl_ops.gl.p_glEnable(GL_STENCIL_TEST);
934 checkGLcall("glEnable GL_STENCIL_TEST");
935 gl_info->gl_ops.gl.p_glStencilFunc(func, ref, mask);
936 checkGLcall("glStencilFunc(...)");
937 gl_info->gl_ops.gl.p_glStencilOp(stencilFail, depthFail, stencilPass);
938 checkGLcall("glStencilOp(...)");
942 gl_info->gl_ops.gl.p_glDisable(GL_STENCIL_TEST);
943 checkGLcall("glDisable GL_STENCIL_TEST");
947 static void state_stencilwrite2s(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
949 DWORD mask = state->fb->depth_stencil ? state->render_states[WINED3D_RS_STENCILWRITEMASK] : 0;
950 const struct wined3d_gl_info *gl_info = context->gl_info;
952 GL_EXTCALL(glActiveStencilFaceEXT(GL_BACK));
953 checkGLcall("glActiveStencilFaceEXT(GL_BACK)");
954 gl_info->gl_ops.gl.p_glStencilMask(mask);
955 checkGLcall("glStencilMask");
956 GL_EXTCALL(glActiveStencilFaceEXT(GL_FRONT));
957 checkGLcall("glActiveStencilFaceEXT(GL_FRONT)");
958 gl_info->gl_ops.gl.p_glStencilMask(mask);
961 static void state_stencilwrite(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
963 DWORD mask = state->fb->depth_stencil ? state->render_states[WINED3D_RS_STENCILWRITEMASK] : 0;
964 const struct wined3d_gl_info *gl_info = context->gl_info;
966 gl_info->gl_ops.gl.p_glStencilMask(mask);
967 checkGLcall("glStencilMask");
970 static void state_fog_vertexpart(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
972 const struct wined3d_gl_info *gl_info = context->gl_info;
974 TRACE("context %p, state %p, state_id %#x.\n", context, state, state_id);
976 if (!state->render_states[WINED3D_RS_FOGENABLE])
979 /* Table fog on: Never use fog coords, and use per-fragment fog */
980 if (state->render_states[WINED3D_RS_FOGTABLEMODE] != WINED3D_FOG_NONE)
982 gl_info->gl_ops.gl.p_glHint(GL_FOG_HINT, GL_NICEST);
983 if (context->fog_coord)
985 gl_info->gl_ops.gl.p_glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
986 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT)");
987 context->fog_coord = FALSE;
990 /* Range fog is only used with per-vertex fog in d3d */
991 if (gl_info->supported[NV_FOG_DISTANCE])
993 gl_info->gl_ops.gl.p_glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_PLANE_ABSOLUTE_NV);
994 checkGLcall("glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_PLANE_ABSOLUTE_NV)");
999 /* Otherwise use per-vertex fog in any case */
1000 gl_info->gl_ops.gl.p_glHint(GL_FOG_HINT, GL_FASTEST);
1002 if (state->render_states[WINED3D_RS_FOGVERTEXMODE] == WINED3D_FOG_NONE || context->last_was_rhw)
1004 /* No fog at all, or transformed vertices: Use fog coord */
1005 if (!context->fog_coord)
1007 gl_info->gl_ops.gl.p_glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FOG_COORDINATE_EXT);
1008 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FOG_COORDINATE_EXT)");
1009 context->fog_coord = TRUE;
1014 /* Otherwise, use the fragment depth */
1015 if (context->fog_coord)
1017 gl_info->gl_ops.gl.p_glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT);
1018 checkGLcall("glFogi(GL_FOG_COORDINATE_SOURCE_EXT, GL_FRAGMENT_DEPTH_EXT)");
1019 context->fog_coord = FALSE;
1022 if (state->render_states[WINED3D_RS_RANGEFOGENABLE])
1024 if (gl_info->supported[NV_FOG_DISTANCE])
1026 gl_info->gl_ops.gl.p_glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_RADIAL_NV);
1027 checkGLcall("glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_RADIAL_NV)");
1031 WARN("Range fog enabled, but not supported by this GL implementation.\n");
1034 else if (gl_info->supported[NV_FOG_DISTANCE])
1036 gl_info->gl_ops.gl.p_glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_PLANE_ABSOLUTE_NV);
1037 checkGLcall("glFogi(GL_FOG_DISTANCE_MODE_NV, GL_EYE_PLANE_ABSOLUTE_NV)");
1042 void state_fogstartend(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1044 const struct wined3d_gl_info *gl_info = context->gl_info;
1045 float fogstart, fogend;
1051 switch(context->fog_source) {
1057 case FOGSOURCE_COORD:
1063 tmpvalue.d = state->render_states[WINED3D_RS_FOGSTART];
1064 fogstart = tmpvalue.f;
1065 tmpvalue.d = state->render_states[WINED3D_RS_FOGEND];
1066 fogend = tmpvalue.f;
1067 /* In GL, fogstart == fogend disables fog, in D3D everything's fogged.*/
1068 if(fogstart == fogend) {
1069 fogstart = -INFINITY;
1075 /* This should not happen.context->fog_source is set in wined3d, not the app.
1076 * Still this is needed to make the compiler happy
1078 ERR("Unexpected fog coordinate source\n");
1083 gl_info->gl_ops.gl.p_glFogf(GL_FOG_START, fogstart);
1084 checkGLcall("glFogf(GL_FOG_START, fogstart)");
1085 TRACE("Fog Start == %f\n", fogstart);
1087 gl_info->gl_ops.gl.p_glFogf(GL_FOG_END, fogend);
1088 checkGLcall("glFogf(GL_FOG_END, fogend)");
1089 TRACE("Fog End == %f\n", fogend);
1092 void state_fog_fragpart(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1094 const struct wined3d_gl_info *gl_info = context->gl_info;
1095 enum fogsource new_source;
1097 TRACE("context %p, state %p, state_id %#x.\n", context, state, state_id);
1099 if (!state->render_states[WINED3D_RS_FOGENABLE])
1101 /* No fog? Disable it, and we're done :-) */
1102 glDisableWINE(GL_FOG);
1103 checkGLcall("glDisable GL_FOG");
1109 * With fixed function vertex processing, Direct3D knows 2 different fog input sources.
1110 * It can use the Z value of the vertex, or the alpha component of the specular color.
1111 * This depends on the fog vertex, fog table and the vertex declaration. If the Z value
1112 * is used, fogstart, fogend and the equation type are used, otherwise linear fog with
1113 * start = 255, end = 0 is used. Obviously the msdn is not very clear on that.
1115 * FOGTABLEMODE != NONE:
1116 * The Z value is used, with the equation specified, no matter what vertex type.
1118 * FOGTABLEMODE == NONE, FOGVERTEXMODE != NONE, untransformed:
1119 * Per vertex fog is calculated using the specified fog equation and the parameters
1121 * FOGTABLEMODE == NONE, FOGVERTEXMODE != NONE, transformed, OR
1122 * FOGTABLEMODE == NONE, FOGVERTEXMODE == NONE, untransformed:
1123 * Linear fog with start = 255.0, end = 0.0, input comes from the specular color
1126 * Rules for vertex fog with shaders:
1128 * When mixing fixed function functionality with the programmable pipeline, D3D expects
1129 * the fog computation to happen during transformation while openGL expects it to happen
1130 * during rasterization. Also, prior to pixel shader 3.0 D3D handles fog blending after
1131 * the pixel shader while openGL always expects the pixel shader to handle the blending.
1132 * To solve this problem, WineD3D does:
1133 * 1) implement a linear fog equation and fog blending at the end of every pre 3.0 pixel
1135 * and 2) disables the fog computation (in either the fixed function or programmable
1136 * rasterizer) if using a vertex program.
1138 * D3D shaders can provide an explicit fog coordinate. This fog coordinate is used with
1139 * D3DRS_FOGTABLEMODE==D3DFOG_NONE. The FOGVERTEXMODE is ignored, d3d always uses linear
1140 * fog with start=1.0 and end=0.0 in this case. This is similar to fog coordinates in
1141 * the specular color, a vertex shader counts as pretransformed geometry in this case.
1142 * There are some GL differences between specular fog coords and vertex shaders though.
1144 * With table fog the vertex shader fog coordinate is ignored.
1146 * If a fogtablemode and a fogvertexmode are specified, table fog is applied (with or
1150 /* DX 7 sdk: "If both render states(vertex and table fog) are set to valid modes,
1151 * the system will apply only pixel(=table) fog effects."
1153 if (state->render_states[WINED3D_RS_FOGTABLEMODE] == WINED3D_FOG_NONE)
1157 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_LINEAR);
1158 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR)");
1159 new_source = FOGSOURCE_VS;
1163 switch (state->render_states[WINED3D_RS_FOGVERTEXMODE])
1165 /* If processed vertices are used, fall through to the NONE case */
1166 case WINED3D_FOG_EXP:
1167 if (!context->last_was_rhw)
1169 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_EXP);
1170 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP)");
1171 new_source = FOGSOURCE_FFP;
1176 case WINED3D_FOG_EXP2:
1177 if (!context->last_was_rhw)
1179 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_EXP2);
1180 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP2)");
1181 new_source = FOGSOURCE_FFP;
1186 case WINED3D_FOG_LINEAR:
1187 if (!context->last_was_rhw)
1189 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_LINEAR);
1190 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR)");
1191 new_source = FOGSOURCE_FFP;
1196 case WINED3D_FOG_NONE:
1197 /* Both are none? According to msdn the alpha channel of the specular
1198 * color contains a fog factor. Set it in drawStridedSlow.
1199 * Same happens with Vertexfog on transformed vertices
1201 new_source = FOGSOURCE_COORD;
1202 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_LINEAR);
1203 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR)");
1207 FIXME("Unexpected WINED3D_RS_FOGVERTEXMODE %#x.\n",
1208 state->render_states[WINED3D_RS_FOGVERTEXMODE]);
1209 new_source = FOGSOURCE_FFP; /* Make the compiler happy */
1213 new_source = FOGSOURCE_FFP;
1215 switch (state->render_states[WINED3D_RS_FOGTABLEMODE])
1217 case WINED3D_FOG_EXP:
1218 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_EXP);
1219 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP)");
1222 case WINED3D_FOG_EXP2:
1223 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_EXP2);
1224 checkGLcall("glFogi(GL_FOG_MODE, GL_EXP2)");
1227 case WINED3D_FOG_LINEAR:
1228 gl_info->gl_ops.gl.p_glFogi(GL_FOG_MODE, GL_LINEAR);
1229 checkGLcall("glFogi(GL_FOG_MODE, GL_LINEAR)");
1232 case WINED3D_FOG_NONE: /* Won't happen */
1234 FIXME("Unexpected WINED3D_RS_FOGTABLEMODE %#x.\n",
1235 state->render_states[WINED3D_RS_FOGTABLEMODE]);
1239 glEnableWINE(GL_FOG);
1240 checkGLcall("glEnable GL_FOG");
1241 if (new_source != context->fog_source)
1243 context->fog_source = new_source;
1244 state_fogstartend(context, state, STATE_RENDER(WINED3D_RS_FOGSTART));
1248 void state_fogcolor(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1250 const struct wined3d_gl_info *gl_info = context->gl_info;
1253 D3DCOLORTOGLFLOAT4(state->render_states[WINED3D_RS_FOGCOLOR], col);
1254 gl_info->gl_ops.gl.p_glFogfv(GL_FOG_COLOR, &col[0]);
1255 checkGLcall("glFog GL_FOG_COLOR");
1258 void state_fogdensity(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1260 const struct wined3d_gl_info *gl_info = context->gl_info;
1266 tmpvalue.d = state->render_states[WINED3D_RS_FOGDENSITY];
1267 gl_info->gl_ops.gl.p_glFogfv(GL_FOG_DENSITY, &tmpvalue.f);
1268 checkGLcall("glFogf(GL_FOG_DENSITY, (float) Value)");
1271 static void state_colormat(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1273 const struct wined3d_device *device = context->swapchain->device;
1274 const struct wined3d_gl_info *gl_info = context->gl_info;
1277 /* Depends on the decoded vertex declaration to read the existence of diffuse data.
1278 * The vertex declaration will call this function if the fixed function pipeline is used.
1281 if(isStateDirty(context, STATE_VDECL)) {
1285 context->num_untracked_materials = 0;
1286 if ((device->strided_streams.use_map & (1 << WINED3D_FFP_DIFFUSE))
1287 && state->render_states[WINED3D_RS_COLORVERTEX])
1289 TRACE("diff %d, amb %d, emis %d, spec %d\n",
1290 state->render_states[WINED3D_RS_DIFFUSEMATERIALSOURCE],
1291 state->render_states[WINED3D_RS_AMBIENTMATERIALSOURCE],
1292 state->render_states[WINED3D_RS_EMISSIVEMATERIALSOURCE],
1293 state->render_states[WINED3D_RS_SPECULARMATERIALSOURCE]);
1295 if (state->render_states[WINED3D_RS_DIFFUSEMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1297 if (state->render_states[WINED3D_RS_AMBIENTMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1298 Parm = GL_AMBIENT_AND_DIFFUSE;
1301 if (state->render_states[WINED3D_RS_EMISSIVEMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1303 context->untracked_materials[context->num_untracked_materials] = GL_EMISSION;
1304 context->num_untracked_materials++;
1306 if (state->render_states[WINED3D_RS_SPECULARMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1308 context->untracked_materials[context->num_untracked_materials] = GL_SPECULAR;
1309 context->num_untracked_materials++;
1312 else if (state->render_states[WINED3D_RS_AMBIENTMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1315 if (state->render_states[WINED3D_RS_EMISSIVEMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1317 context->untracked_materials[context->num_untracked_materials] = GL_EMISSION;
1318 context->num_untracked_materials++;
1320 if (state->render_states[WINED3D_RS_SPECULARMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1322 context->untracked_materials[context->num_untracked_materials] = GL_SPECULAR;
1323 context->num_untracked_materials++;
1326 else if (state->render_states[WINED3D_RS_EMISSIVEMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1329 if (state->render_states[WINED3D_RS_SPECULARMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1331 context->untracked_materials[context->num_untracked_materials] = GL_SPECULAR;
1332 context->num_untracked_materials++;
1335 else if (state->render_states[WINED3D_RS_SPECULARMATERIALSOURCE] == WINED3D_MCS_COLOR1)
1341 /* Nothing changed, return. */
1342 if (Parm == context->tracking_parm) return;
1346 gl_info->gl_ops.gl.p_glDisable(GL_COLOR_MATERIAL);
1347 checkGLcall("glDisable GL_COLOR_MATERIAL");
1351 gl_info->gl_ops.gl.p_glColorMaterial(GL_FRONT_AND_BACK, Parm);
1352 checkGLcall("glColorMaterial(GL_FRONT_AND_BACK, Parm)");
1353 gl_info->gl_ops.gl.p_glEnable(GL_COLOR_MATERIAL);
1354 checkGLcall("glEnable(GL_COLOR_MATERIAL)");
1357 /* Apparently calls to glMaterialfv are ignored for properties we're
1358 * tracking with glColorMaterial, so apply those here. */
1359 switch (context->tracking_parm)
1361 case GL_AMBIENT_AND_DIFFUSE:
1362 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float *)&state->material.ambient);
1363 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float *)&state->material.diffuse);
1364 checkGLcall("glMaterialfv");
1368 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, (float *)&state->material.diffuse);
1369 checkGLcall("glMaterialfv");
1373 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, (float *)&state->material.ambient);
1374 checkGLcall("glMaterialfv");
1378 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, (float *)&state->material.emissive);
1379 checkGLcall("glMaterialfv");
1383 /* Only change material color if specular is enabled, otherwise it is set to black */
1384 if (state->render_states[WINED3D_RS_SPECULARENABLE])
1386 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, (float *)&state->material.specular);
1387 checkGLcall("glMaterialfv");
1391 static const GLfloat black[] = {0.0f, 0.0f, 0.0f, 0.0f};
1392 gl_info->gl_ops.gl.p_glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, &black[0]);
1393 checkGLcall("glMaterialfv");
1398 context->tracking_parm = Parm;
1401 static void state_linepattern(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1403 const struct wined3d_gl_info *gl_info = context->gl_info;
1407 struct wined3d_line_pattern lp;
1409 tmppattern.d = state->render_states[WINED3D_RS_LINEPATTERN];
1411 TRACE("Line pattern: repeat %d bits %x.\n", tmppattern.lp.repeat_factor, tmppattern.lp.line_pattern);
1413 if (tmppattern.lp.repeat_factor)
1415 gl_info->gl_ops.gl.p_glLineStipple(tmppattern.lp.repeat_factor, tmppattern.lp.line_pattern);
1416 checkGLcall("glLineStipple(repeat, linepattern)");
1417 gl_info->gl_ops.gl.p_glEnable(GL_LINE_STIPPLE);
1418 checkGLcall("glEnable(GL_LINE_STIPPLE);");
1422 gl_info->gl_ops.gl.p_glDisable(GL_LINE_STIPPLE);
1423 checkGLcall("glDisable(GL_LINE_STIPPLE);");
1427 static void state_normalize(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1429 const struct wined3d_gl_info *gl_info = context->gl_info;
1431 if (isStateDirty(context, STATE_VDECL))
1434 /* Without vertex normals, we set the current normal to 0/0/0 to remove the diffuse factor
1435 * from the opengl lighting equation, as d3d does. Normalization of 0/0/0 can lead to a division
1436 * by zero and is not properly defined in opengl, so avoid it
1438 if (state->render_states[WINED3D_RS_NORMALIZENORMALS]
1439 && (context->swapchain->device->strided_streams.use_map & (1 << WINED3D_FFP_NORMAL)))
1441 gl_info->gl_ops.gl.p_glEnable(GL_NORMALIZE);
1442 checkGLcall("glEnable(GL_NORMALIZE);");
1446 gl_info->gl_ops.gl.p_glDisable(GL_NORMALIZE);
1447 checkGLcall("glDisable(GL_NORMALIZE);");
1451 static void state_psizemin_w(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1458 tmpvalue.d = state->render_states[WINED3D_RS_POINTSIZE_MIN];
1459 if (tmpvalue.f != 1.0f)
1461 FIXME("WINED3D_RS_POINTSIZE_MIN not supported on this opengl, value is %f\n", tmpvalue.f);
1463 tmpvalue.d = state->render_states[WINED3D_RS_POINTSIZE_MAX];
1464 if (tmpvalue.f != 64.0f)
1466 FIXME("WINED3D_RS_POINTSIZE_MAX not supported on this opengl, value is %f\n", tmpvalue.f);
1471 static void state_psizemin_ext(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1473 const struct wined3d_gl_info *gl_info = context->gl_info;
1480 min.d = state->render_states[WINED3D_RS_POINTSIZE_MIN];
1481 max.d = state->render_states[WINED3D_RS_POINTSIZE_MAX];
1483 /* Max point size trumps min point size */
1488 GL_EXTCALL(glPointParameterfEXT)(GL_POINT_SIZE_MIN_EXT, min.f);
1489 checkGLcall("glPointParameterfEXT(...)");
1490 GL_EXTCALL(glPointParameterfEXT)(GL_POINT_SIZE_MAX_EXT, max.f);
1491 checkGLcall("glPointParameterfEXT(...)");
1494 static void state_psizemin_arb(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1496 const struct wined3d_gl_info *gl_info = context->gl_info;
1503 min.d = state->render_states[WINED3D_RS_POINTSIZE_MIN];
1504 max.d = state->render_states[WINED3D_RS_POINTSIZE_MAX];
1506 /* Max point size trumps min point size */
1511 GL_EXTCALL(glPointParameterfARB)(GL_POINT_SIZE_MIN_ARB, min.f);
1512 checkGLcall("glPointParameterfARB(...)");
1513 GL_EXTCALL(glPointParameterfARB)(GL_POINT_SIZE_MAX_ARB, max.f);
1514 checkGLcall("glPointParameterfARB(...)");
1517 static void state_pscale(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1519 const struct wined3d_gl_info *gl_info = context->gl_info;
1520 /* TODO: Group this with the viewport */
1522 * POINTSCALEENABLE controls how point size value is treated. If set to
1523 * true, the point size is scaled with respect to height of viewport.
1524 * When set to false point size is in pixels.
1527 /* Default values */
1528 GLfloat att[3] = {1.0f, 0.0f, 0.0f};
1532 } pointSize, A, B, C;
1534 pointSize.d = state->render_states[WINED3D_RS_POINTSIZE];
1535 A.d = state->render_states[WINED3D_RS_POINTSCALE_A];
1536 B.d = state->render_states[WINED3D_RS_POINTSCALE_B];
1537 C.d = state->render_states[WINED3D_RS_POINTSCALE_C];
1539 if (state->render_states[WINED3D_RS_POINTSCALEENABLE])
1541 DWORD h = state->viewport.height;
1542 GLfloat scaleFactor;
1544 if (pointSize.f < gl_info->limits.pointsize_min)
1546 /* Minimum valid point size for OpenGL is driver specific. For Direct3D it is
1547 * 0.0f. This means that OpenGL will clamp really small point sizes to the
1548 * driver minimum. To correct for this we need to multiply by the scale factor when sizes
1549 * are less than 1.0f. scale_factor = 1.0f / point_size.
1551 scaleFactor = pointSize.f / gl_info->limits.pointsize_min;
1552 /* Clamp the point size, don't rely on the driver to do it. MacOS says min point size
1553 * is 1.0, but then accepts points below that and draws too small points
1555 pointSize.f = gl_info->limits.pointsize_min;
1557 else if(pointSize.f > gl_info->limits.pointsize_max)
1559 /* gl already scales the input to glPointSize,
1560 * d3d scales the result after the point size scale.
1561 * If the point size is bigger than the max size, use the
1562 * scaling to scale it bigger, and set the gl point size to max
1564 scaleFactor = pointSize.f / gl_info->limits.pointsize_max;
1565 TRACE("scale: %f\n", scaleFactor);
1566 pointSize.f = gl_info->limits.pointsize_max;
1570 scaleFactor = powf(h * scaleFactor, 2);
1572 att[0] = A.f / scaleFactor;
1573 att[1] = B.f / scaleFactor;
1574 att[2] = C.f / scaleFactor;
1577 if (gl_info->supported[ARB_POINT_PARAMETERS])
1579 GL_EXTCALL(glPointParameterfvARB)(GL_POINT_DISTANCE_ATTENUATION_ARB, att);
1580 checkGLcall("glPointParameterfvARB(GL_DISTANCE_ATTENUATION_ARB, ...)");
1582 else if (gl_info->supported[EXT_POINT_PARAMETERS])
1584 GL_EXTCALL(glPointParameterfvEXT)(GL_DISTANCE_ATTENUATION_EXT, att);
1585 checkGLcall("glPointParameterfvEXT(GL_DISTANCE_ATTENUATION_EXT, ...)");
1587 else if (state->render_states[WINED3D_RS_POINTSCALEENABLE])
1589 WARN("POINT_PARAMETERS not supported in this version of opengl\n");
1592 gl_info->gl_ops.gl.p_glPointSize(pointSize.f);
1593 checkGLcall("glPointSize(...);");
1596 static void state_debug_monitor(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1598 WARN("token: %#x.\n", state->render_states[WINED3D_RS_DEBUGMONITORTOKEN]);
1601 static void state_colorwrite(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1603 DWORD mask0 = state->render_states[WINED3D_RS_COLORWRITEENABLE];
1604 DWORD mask1 = state->render_states[WINED3D_RS_COLORWRITEENABLE1];
1605 DWORD mask2 = state->render_states[WINED3D_RS_COLORWRITEENABLE2];
1606 DWORD mask3 = state->render_states[WINED3D_RS_COLORWRITEENABLE3];
1607 const struct wined3d_gl_info *gl_info = context->gl_info;
1609 TRACE("Color mask: r(%d) g(%d) b(%d) a(%d)\n",
1610 mask0 & WINED3DCOLORWRITEENABLE_RED ? 1 : 0,
1611 mask0 & WINED3DCOLORWRITEENABLE_GREEN ? 1 : 0,
1612 mask0 & WINED3DCOLORWRITEENABLE_BLUE ? 1 : 0,
1613 mask0 & WINED3DCOLORWRITEENABLE_ALPHA ? 1 : 0);
1614 gl_info->gl_ops.gl.p_glColorMask(mask0 & WINED3DCOLORWRITEENABLE_RED ? GL_TRUE : GL_FALSE,
1615 mask0 & WINED3DCOLORWRITEENABLE_GREEN ? GL_TRUE : GL_FALSE,
1616 mask0 & WINED3DCOLORWRITEENABLE_BLUE ? GL_TRUE : GL_FALSE,
1617 mask0 & WINED3DCOLORWRITEENABLE_ALPHA ? GL_TRUE : GL_FALSE);
1618 checkGLcall("glColorMask(...)");
1620 if (!((mask1 == mask0 && mask2 == mask0 && mask3 == mask0)
1621 || (mask1 == 0xf && mask2 == 0xf && mask3 == 0xf)))
1623 FIXME("WINED3D_RS_COLORWRITEENABLE/1/2/3, %#x/%#x/%#x/%#x not yet implemented.\n",
1624 mask0, mask1, mask2, mask3);
1625 FIXME("Missing of cap D3DPMISCCAPS_INDEPENDENTWRITEMASKS wasn't honored?\n");
1629 static void set_color_mask(const struct wined3d_gl_info *gl_info, UINT index, DWORD mask)
1631 GL_EXTCALL(glColorMaskIndexedEXT(index,
1632 mask & WINED3DCOLORWRITEENABLE_RED ? GL_TRUE : GL_FALSE,
1633 mask & WINED3DCOLORWRITEENABLE_GREEN ? GL_TRUE : GL_FALSE,
1634 mask & WINED3DCOLORWRITEENABLE_BLUE ? GL_TRUE : GL_FALSE,
1635 mask & WINED3DCOLORWRITEENABLE_ALPHA ? GL_TRUE : GL_FALSE));
1638 static void state_colorwrite0(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1640 set_color_mask(context->gl_info, 0, state->render_states[WINED3D_RS_COLORWRITEENABLE]);
1643 static void state_colorwrite1(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1645 set_color_mask(context->gl_info, 1, state->render_states[WINED3D_RS_COLORWRITEENABLE1]);
1648 static void state_colorwrite2(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1650 set_color_mask(context->gl_info, 2, state->render_states[WINED3D_RS_COLORWRITEENABLE2]);
1653 static void state_colorwrite3(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1655 set_color_mask(context->gl_info, 3, state->render_states[WINED3D_RS_COLORWRITEENABLE3]);
1658 static void state_localviewer(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1660 const struct wined3d_gl_info *gl_info = context->gl_info;
1662 if (state->render_states[WINED3D_RS_LOCALVIEWER])
1664 gl_info->gl_ops.gl.p_glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 1);
1665 checkGLcall("glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 1)");
1669 gl_info->gl_ops.gl.p_glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 0);
1670 checkGLcall("glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 0)");
1674 static void state_lastpixel(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1676 if (state->render_states[WINED3D_RS_LASTPIXEL])
1678 TRACE("Last Pixel Drawing Enabled\n");
1684 FIXME("Last Pixel Drawing Disabled, not handled yet\n");
1687 TRACE("Last Pixel Drawing Disabled, not handled yet\n");
1692 static void state_pointsprite_w(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1696 /* TODO: NV_POINT_SPRITE */
1697 if (!warned && state->render_states[WINED3D_RS_POINTSPRITEENABLE])
1699 /* A FIXME, not a WARN because point sprites should be software emulated if not supported by HW */
1700 FIXME("Point sprites not supported\n");
1705 static void state_pointsprite(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1707 const struct wined3d_gl_info *gl_info = context->gl_info;
1709 if (state->render_states[WINED3D_RS_POINTSPRITEENABLE])
1711 gl_info->gl_ops.gl.p_glEnable(GL_POINT_SPRITE_ARB);
1712 checkGLcall("glEnable(GL_POINT_SPRITE_ARB)");
1716 gl_info->gl_ops.gl.p_glDisable(GL_POINT_SPRITE_ARB);
1717 checkGLcall("glDisable(GL_POINT_SPRITE_ARB)");
1721 static void state_wrap(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1723 if (state->render_states[WINED3D_RS_WRAP0]
1724 || state->render_states[WINED3D_RS_WRAP1]
1725 || state->render_states[WINED3D_RS_WRAP2]
1726 || state->render_states[WINED3D_RS_WRAP3]
1727 || state->render_states[WINED3D_RS_WRAP4]
1728 || state->render_states[WINED3D_RS_WRAP5]
1729 || state->render_states[WINED3D_RS_WRAP6]
1730 || state->render_states[WINED3D_RS_WRAP7]
1731 || state->render_states[WINED3D_RS_WRAP8]
1732 || state->render_states[WINED3D_RS_WRAP9]
1733 || state->render_states[WINED3D_RS_WRAP10]
1734 || state->render_states[WINED3D_RS_WRAP11]
1735 || state->render_states[WINED3D_RS_WRAP12]
1736 || state->render_states[WINED3D_RS_WRAP13]
1737 || state->render_states[WINED3D_RS_WRAP14]
1738 || state->render_states[WINED3D_RS_WRAP15])
1739 FIXME("(WINED3D_RS_WRAP0) Texture wrapping not yet supported.\n");
1742 static void state_msaa_w(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1744 if (state->render_states[WINED3D_RS_MULTISAMPLEANTIALIAS])
1745 WARN("Multisample antialiasing not supported by GL.\n");
1748 static void state_msaa(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1750 const struct wined3d_gl_info *gl_info = context->gl_info;
1752 if (state->render_states[WINED3D_RS_MULTISAMPLEANTIALIAS])
1754 gl_info->gl_ops.gl.p_glEnable(GL_MULTISAMPLE_ARB);
1755 checkGLcall("glEnable(GL_MULTISAMPLE_ARB)");
1759 gl_info->gl_ops.gl.p_glDisable(GL_MULTISAMPLE_ARB);
1760 checkGLcall("glDisable(GL_MULTISAMPLE_ARB)");
1764 static void state_scissor(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1766 const struct wined3d_gl_info *gl_info = context->gl_info;
1768 if (state->render_states[WINED3D_RS_SCISSORTESTENABLE])
1770 gl_info->gl_ops.gl.p_glEnable(GL_SCISSOR_TEST);
1771 checkGLcall("glEnable(GL_SCISSOR_TEST)");
1775 gl_info->gl_ops.gl.p_glDisable(GL_SCISSOR_TEST);
1776 checkGLcall("glDisable(GL_SCISSOR_TEST)");
1780 /* The Direct3D depth bias is specified in normalized depth coordinates. In
1781 * OpenGL the bias is specified in units of "the smallest value that is
1782 * guaranteed to produce a resolvable offset for a given implementation". To
1783 * convert from D3D to GL we need to divide the D3D depth bias by that value.
1784 * There's no practical way to retrieve that value from a given GL
1785 * implementation, but the D3D application has essentially the same problem,
1786 * which makes a guess of the depth buffer format's highest possible value a
1787 * reasonable guess. Note that SLOPESCALEDEPTHBIAS is a scaling factor for the
1788 * depth slope, and doesn't need to be scaled. */
1789 static void state_depthbias(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1791 const struct wined3d_gl_info *gl_info = context->gl_info;
1793 if (state->render_states[WINED3D_RS_SLOPESCALEDEPTHBIAS]
1794 || state->render_states[WINED3D_RS_DEPTHBIAS])
1796 const struct wined3d_surface *depth = state->fb->depth_stencil;
1803 } scale_bias, const_bias;
1805 scale_bias.d = state->render_states[WINED3D_RS_SLOPESCALEDEPTHBIAS];
1806 const_bias.d = state->render_states[WINED3D_RS_DEPTHBIAS];
1808 gl_info->gl_ops.gl.p_glEnable(GL_POLYGON_OFFSET_FILL);
1809 checkGLcall("glEnable(GL_POLYGON_OFFSET_FILL)");
1811 if (context->swapchain->device->wined3d->flags & WINED3D_LEGACY_DEPTH_BIAS)
1813 float bias = -(float)const_bias.d;
1814 gl_info->gl_ops.gl.p_glPolygonOffset(bias, bias);
1815 checkGLcall("glPolygonOffset");
1821 const struct wined3d_format *fmt = depth->resource.format;
1822 scale = powf(2, fmt->depth_size) - 1;
1823 TRACE("Depth format %s, using depthbias scale of %.8e.\n",
1824 debug_d3dformat(fmt->id), scale);
1828 /* The context manager will reapply this state on a depth stencil change */
1829 TRACE("No depth stencil, using depthbias scale of 0.0.\n");
1833 gl_info->gl_ops.gl.p_glPolygonOffset(scale_bias.f, const_bias.f * scale);
1834 checkGLcall("glPolygonOffset(...)");
1839 gl_info->gl_ops.gl.p_glDisable(GL_POLYGON_OFFSET_FILL);
1840 checkGLcall("glDisable(GL_POLYGON_OFFSET_FILL)");
1844 static void state_zvisible(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1846 if (state->render_states[WINED3D_RS_ZVISIBLE])
1847 FIXME("WINED3D_RS_ZVISIBLE not implemented.\n");
1850 static void state_perspective(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1852 const struct wined3d_gl_info *gl_info = context->gl_info;
1854 if (state->render_states[WINED3D_RS_TEXTUREPERSPECTIVE])
1856 gl_info->gl_ops.gl.p_glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
1857 checkGLcall("glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST)");
1861 gl_info->gl_ops.gl.p_glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST);
1862 checkGLcall("glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST)");
1866 static void state_stippledalpha(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1868 if (state->render_states[WINED3D_RS_STIPPLEDALPHA])
1869 FIXME("Stippled Alpha not supported yet.\n");
1872 static void state_antialias(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1874 if (state->render_states[WINED3D_RS_ANTIALIAS])
1875 FIXME("Antialias not supported yet.\n");
1878 static void state_multisampmask(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1880 if (state->render_states[WINED3D_RS_MULTISAMPLEMASK] != 0xffffffff)
1881 FIXME("WINED3D_RS_MULTISAMPLEMASK %#x not yet implemented.\n",
1882 state->render_states[WINED3D_RS_MULTISAMPLEMASK]);
1885 static void state_patchedgestyle(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1887 if (state->render_states[WINED3D_RS_PATCHEDGESTYLE] != WINED3D_PATCH_EDGE_DISCRETE)
1888 FIXME("WINED3D_RS_PATCHEDGESTYLE %#x not yet implemented.\n",
1889 state->render_states[WINED3D_RS_PATCHEDGESTYLE]);
1892 static void state_patchsegments(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1900 if (state->render_states[WINED3D_RS_PATCHSEGMENTS] != tmpvalue.d)
1902 static BOOL displayed = FALSE;
1904 tmpvalue.d = state->render_states[WINED3D_RS_PATCHSEGMENTS];
1906 FIXME("(WINED3D_RS_PATCHSEGMENTS,%f) not yet implemented\n", tmpvalue.f);
1912 static void state_positiondegree(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1914 if (state->render_states[WINED3D_RS_POSITIONDEGREE] != WINED3D_DEGREE_CUBIC)
1915 FIXME("WINED3D_RS_POSITIONDEGREE %#x not yet implemented.\n",
1916 state->render_states[WINED3D_RS_POSITIONDEGREE]);
1919 static void state_normaldegree(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1921 if (state->render_states[WINED3D_RS_NORMALDEGREE] != WINED3D_DEGREE_LINEAR)
1922 FIXME("WINED3D_RS_NORMALDEGREE %#x not yet implemented.\n",
1923 state->render_states[WINED3D_RS_NORMALDEGREE]);
1926 static void state_tessellation(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1928 if (state->render_states[WINED3D_RS_ENABLEADAPTIVETESSELLATION])
1929 FIXME("WINED3D_RS_ENABLEADAPTIVETESSELLATION %#x not yet implemented.\n",
1930 state->render_states[WINED3D_RS_ENABLEADAPTIVETESSELLATION]);
1933 static void state_nvdb(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1940 const struct wined3d_gl_info *gl_info = context->gl_info;
1942 if (state->render_states[WINED3D_RS_ADAPTIVETESS_X] == WINED3DFMT_NVDB)
1944 zmin.d = state->render_states[WINED3D_RS_ADAPTIVETESS_Z];
1945 zmax.d = state->render_states[WINED3D_RS_ADAPTIVETESS_W];
1947 /* If zmin is larger than zmax INVALID_VALUE error is generated.
1948 * In d3d9 test is not performed in this case*/
1949 if (zmin.f <= zmax.f)
1951 gl_info->gl_ops.gl.p_glEnable(GL_DEPTH_BOUNDS_TEST_EXT);
1952 checkGLcall("glEnable(GL_DEPTH_BOUNDS_TEST_EXT)");
1953 GL_EXTCALL(glDepthBoundsEXT(zmin.f, zmax.f));
1954 checkGLcall("glDepthBoundsEXT(...)");
1958 gl_info->gl_ops.gl.p_glDisable(GL_DEPTH_BOUNDS_TEST_EXT);
1959 checkGLcall("glDisable(GL_DEPTH_BOUNDS_TEST_EXT)");
1964 gl_info->gl_ops.gl.p_glDisable(GL_DEPTH_BOUNDS_TEST_EXT);
1965 checkGLcall("glDisable(GL_DEPTH_BOUNDS_TEST_EXT)");
1968 state_tessellation(context, state, STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION));
1971 static void state_wrapu(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1973 if (state->render_states[WINED3D_RS_WRAPU])
1974 FIXME("Render state WINED3D_RS_WRAPU not implemented yet.\n");
1977 static void state_wrapv(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1979 if (state->render_states[WINED3D_RS_WRAPV])
1980 FIXME("Render state WINED3D_RS_WRAPV not implemented yet.\n");
1983 static void state_monoenable(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1985 if (state->render_states[WINED3D_RS_MONOENABLE])
1986 FIXME("Render state WINED3D_RS_MONOENABLE not implemented yet.\n");
1989 static void state_rop2(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1991 if (state->render_states[WINED3D_RS_ROP2])
1992 FIXME("Render state WINED3D_RS_ROP2 not implemented yet.\n");
1995 static void state_planemask(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
1997 if (state->render_states[WINED3D_RS_PLANEMASK])
1998 FIXME("Render state WINED3D_RS_PLANEMASK not implemented yet.\n");
2001 static void state_subpixel(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2003 if (state->render_states[WINED3D_RS_SUBPIXEL])
2004 FIXME("Render state WINED3D_RS_SUBPIXEL not implemented yet.\n");
2007 static void state_subpixelx(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2009 if (state->render_states[WINED3D_RS_SUBPIXELX])
2010 FIXME("Render state WINED3D_RS_SUBPIXELX not implemented yet.\n");
2013 static void state_stippleenable(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2015 if (state->render_states[WINED3D_RS_STIPPLEENABLE])
2016 FIXME("Render state WINED3D_RS_STIPPLEENABLE not implemented yet.\n");
2019 static void state_mipmaplodbias(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2021 if (state->render_states[WINED3D_RS_MIPMAPLODBIAS])
2022 FIXME("Render state WINED3D_RS_MIPMAPLODBIAS not implemented yet.\n");
2025 static void state_anisotropy(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2027 if (state->render_states[WINED3D_RS_ANISOTROPY])
2028 FIXME("Render state WINED3D_RS_ANISOTROPY not implemented yet.\n");
2031 static void state_flushbatch(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2033 if (state->render_states[WINED3D_RS_FLUSHBATCH])
2034 FIXME("Render state WINED3D_RS_FLUSHBATCH not implemented yet.\n");
2037 static void state_translucentsi(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2039 if (state->render_states[WINED3D_RS_TRANSLUCENTSORTINDEPENDENT])
2040 FIXME("Render state WINED3D_RS_TRANSLUCENTSORTINDEPENDENT not implemented yet.\n");
2043 static void state_extents(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2045 if (state->render_states[WINED3D_RS_EXTENTS])
2046 FIXME("Render state WINED3D_RS_EXTENTS not implemented yet.\n");
2049 static void state_ckeyblend(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2051 if (state->render_states[WINED3D_RS_COLORKEYBLENDENABLE])
2052 FIXME("Render state WINED3D_RS_COLORKEYBLENDENABLE not implemented yet.\n");
2055 static void state_swvp(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
2057 if (state->render_states[WINED3D_RS_SOFTWAREVERTEXPROCESSING])
2058 FIXME("Software vertex processing not implemented.\n");
2061 static void get_src_and_opr(DWORD arg, BOOL is_alpha, GLenum* source, GLenum* operand) {
2062 /* The WINED3DTA_ALPHAREPLICATE flag specifies the alpha component of the
2063 * input should be used for all input components. The WINED3DTA_COMPLEMENT
2064 * flag specifies the complement of the input should be used. */
2065 BOOL from_alpha = is_alpha || arg & WINED3DTA_ALPHAREPLICATE;
2066 BOOL complement = arg & WINED3DTA_COMPLEMENT;
2068 /* Calculate the operand */
2070 if (from_alpha) *operand = GL_ONE_MINUS_SRC_ALPHA;
2071 else *operand = GL_ONE_MINUS_SRC_COLOR;
2073 if (from_alpha) *operand = GL_SRC_ALPHA;
2074 else *operand = GL_SRC_COLOR;
2077 /* Calculate the source */
2078 switch (arg & WINED3DTA_SELECTMASK) {
2079 case WINED3DTA_CURRENT: *source = GL_PREVIOUS_EXT; break;
2080 case WINED3DTA_DIFFUSE: *source = GL_PRIMARY_COLOR_EXT; break;
2081 case WINED3DTA_TEXTURE: *source = GL_TEXTURE; break;
2082 case WINED3DTA_TFACTOR: *source = GL_CONSTANT_EXT; break;
2083 case WINED3DTA_SPECULAR:
2085 * According to the GL_ARB_texture_env_combine specs, SPECULAR is
2086 * 'Secondary color' and isn't supported until base GL supports it
2087 * There is no concept of temp registers as far as I can tell
2089 FIXME("Unhandled texture arg WINED3DTA_SPECULAR\n");
2090 *source = GL_TEXTURE;
2093 FIXME("Unrecognized texture arg %#x\n", arg);
2094 *source = GL_TEXTURE;
2099 /* Setup the texture operations texture stage states */
2100 static void set_tex_op(const struct wined3d_gl_info *gl_info, const struct wined3d_state *state,
2101 BOOL isAlpha, int Stage, enum wined3d_texture_op op, DWORD arg1, DWORD arg2, DWORD arg3)
2103 GLenum src1, src2, src3;
2104 GLenum opr1, opr2, opr3;
2106 GLenum src0_target, src1_target, src2_target;
2107 GLenum opr0_target, opr1_target, opr2_target;
2109 GLenum opr=0, invopr, src3_target, opr3_target;
2110 BOOL Handled = FALSE;
2112 TRACE("Alpha?(%d), Stage:%d Op(%s), a1(%d), a2(%d), a3(%d)\n", isAlpha, Stage, debug_d3dtop(op), arg1, arg2, arg3);
2114 /* This is called by a state handler which has the gl lock held and a context for the thread */
2116 /* Note: Operations usually involve two ars, src0 and src1 and are operations of
2117 the form (a1 <operation> a2). However, some of the more complex operations
2118 take 3 parameters. Instead of the (sensible) addition of a3, Microsoft added
2119 in a third parameter called a0. Therefore these are operations of the form
2120 a0 <operation> a1 <operation> a2, i.e., the new parameter goes to the front.
2122 However, below we treat the new (a0) parameter as src2/opr2, so in the actual
2123 functions below, expect their syntax to differ slightly to those listed in the
2124 manuals, i.e., replace arg1 with arg3, arg2 with arg1 and arg3 with arg2
2125 This affects WINED3DTOP_MULTIPLYADD and WINED3DTOP_LERP */
2129 comb_target = GL_COMBINE_ALPHA;
2130 src0_target = GL_SOURCE0_ALPHA;
2131 src1_target = GL_SOURCE1_ALPHA;
2132 src2_target = GL_SOURCE2_ALPHA;
2133 opr0_target = GL_OPERAND0_ALPHA;
2134 opr1_target = GL_OPERAND1_ALPHA;
2135 opr2_target = GL_OPERAND2_ALPHA;
2136 scal_target = GL_ALPHA_SCALE;
2140 comb_target = GL_COMBINE_RGB;
2141 src0_target = GL_SOURCE0_RGB;
2142 src1_target = GL_SOURCE1_RGB;
2143 src2_target = GL_SOURCE2_RGB;
2144 opr0_target = GL_OPERAND0_RGB;
2145 opr1_target = GL_OPERAND1_RGB;
2146 opr2_target = GL_OPERAND2_RGB;
2147 scal_target = GL_RGB_SCALE;
2150 /* If a texture stage references an invalid texture unit the stage just
2151 * passes through the result from the previous stage */
2152 if (is_invalid_op(state, Stage, op, arg1, arg2, arg3))
2154 arg1 = WINED3DTA_CURRENT;
2155 op = WINED3D_TOP_SELECT_ARG1;
2158 if (isAlpha && !state->textures[Stage] && arg1 == WINED3DTA_TEXTURE)
2160 get_src_and_opr(WINED3DTA_DIFFUSE, isAlpha, &src1, &opr1);
2162 get_src_and_opr(arg1, isAlpha, &src1, &opr1);
2164 get_src_and_opr(arg2, isAlpha, &src2, &opr2);
2165 get_src_and_opr(arg3, isAlpha, &src3, &opr3);
2167 TRACE("ct(%x), 1:(%x,%x), 2:(%x,%x), 3:(%x,%x)\n", comb_target, src1, opr1, src2, opr2, src3, opr3);
2169 Handled = TRUE; /* Assume will be handled */
2171 /* Other texture operations require special extensions: */
2172 if (gl_info->supported[NV_TEXTURE_ENV_COMBINE4])
2176 invopr = GL_ONE_MINUS_SRC_ALPHA;
2177 src3_target = GL_SOURCE3_ALPHA_NV;
2178 opr3_target = GL_OPERAND3_ALPHA_NV;
2181 invopr = GL_ONE_MINUS_SRC_COLOR;
2182 src3_target = GL_SOURCE3_RGB_NV;
2183 opr3_target = GL_OPERAND3_RGB_NV;
2187 case WINED3D_TOP_DISABLE: /* Only for alpha */
2188 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2189 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_REPLACE");
2190 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, GL_PREVIOUS_EXT);
2191 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2192 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, GL_SRC_ALPHA);
2193 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2194 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2195 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2196 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2197 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2198 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_ZERO);
2199 checkGLcall("GL_TEXTURE_ENV, src2_target, GL_ZERO");
2200 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr);
2201 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr");
2202 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2203 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2204 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2205 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr");
2208 case WINED3D_TOP_SELECT_ARG1: /* = a1 * 1 + 0 * 0 */
2209 case WINED3D_TOP_SELECT_ARG2: /* = a2 * 1 + 0 * 0 */
2210 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2211 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2212 if (op == WINED3D_TOP_SELECT_ARG1)
2214 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2215 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2216 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2217 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2221 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src2);
2222 checkGLcall("GL_TEXTURE_ENV, src0_target, src2");
2223 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr2);
2224 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr2");
2226 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2227 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2228 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2229 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2230 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_ZERO);
2231 checkGLcall("GL_TEXTURE_ENV, src2_target, GL_ZERO");
2232 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr);
2233 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr");
2234 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2235 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2236 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2237 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr");
2240 case WINED3D_TOP_MODULATE:
2241 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2242 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD"); /* Add = a0*a1 + a2*a3 */
2243 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2244 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2245 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2246 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2247 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2248 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2249 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2250 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2251 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_ZERO);
2252 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2253 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr);
2254 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2255 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2256 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2257 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2258 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr1");
2259 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2260 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2262 case WINED3D_TOP_MODULATE_2X:
2263 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2264 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD"); /* Add = a0*a1 + a2*a3 */
2265 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2266 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2267 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2268 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2269 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2270 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2271 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2272 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2273 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_ZERO);
2274 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2275 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr);
2276 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2277 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2278 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2279 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2280 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr1");
2281 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 2);
2282 checkGLcall("GL_TEXTURE_ENV, scal_target, 2");
2284 case WINED3D_TOP_MODULATE_4X:
2285 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2286 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD"); /* Add = a0*a1 + a2*a3 */
2287 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2288 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2289 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2290 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2291 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2292 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2293 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2294 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2295 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_ZERO);
2296 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2297 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr);
2298 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2299 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2300 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2301 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2302 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr1");
2303 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 4);
2304 checkGLcall("GL_TEXTURE_ENV, scal_target, 4");
2307 case WINED3D_TOP_ADD:
2308 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2309 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2310 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2311 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2312 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2313 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2314 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2315 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2316 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2317 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2318 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2319 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2320 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2321 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2322 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2323 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2324 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, invopr);
2325 checkGLcall("GL_TEXTURE_ENV, opr3_target, invopr");
2326 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2327 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2330 case WINED3D_TOP_ADD_SIGNED:
2331 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED);
2332 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED");
2333 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2334 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2335 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2336 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2337 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2338 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2339 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2340 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2341 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2342 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2343 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2344 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2345 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2346 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2347 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, invopr);
2348 checkGLcall("GL_TEXTURE_ENV, opr3_target, invopr");
2349 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2350 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2353 case WINED3D_TOP_ADD_SIGNED_2X:
2354 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED);
2355 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED");
2356 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2357 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2358 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2359 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2360 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2361 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2362 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2363 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2364 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2365 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2366 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2367 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2368 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2369 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2370 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, invopr);
2371 checkGLcall("GL_TEXTURE_ENV, opr3_target, invopr");
2372 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 2);
2373 checkGLcall("GL_TEXTURE_ENV, scal_target, 2");
2376 case WINED3D_TOP_ADD_SMOOTH:
2377 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2378 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2379 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2380 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2381 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2382 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2383 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2384 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2385 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2386 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2387 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2388 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2389 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2390 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2391 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, src1);
2392 checkGLcall("GL_TEXTURE_ENV, src3_target, src1");
2394 case GL_SRC_COLOR: opr = GL_ONE_MINUS_SRC_COLOR; break;
2395 case GL_ONE_MINUS_SRC_COLOR: opr = GL_SRC_COLOR; break;
2396 case GL_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2397 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
2399 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2400 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr");
2401 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2402 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2405 case WINED3D_TOP_BLEND_DIFFUSE_ALPHA:
2406 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2407 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2408 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2409 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2410 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2411 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2412 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_PRIMARY_COLOR);
2413 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_PRIMARY_COLOR");
2414 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2415 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2416 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2417 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2418 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2419 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2420 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_PRIMARY_COLOR);
2421 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_PRIMARY_COLOR");
2422 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA);
2423 checkGLcall("GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA");
2424 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2425 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2427 case WINED3D_TOP_BLEND_TEXTURE_ALPHA:
2428 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2429 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2430 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2431 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2432 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2433 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2434 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_TEXTURE);
2435 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_TEXTURE");
2436 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2437 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2438 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2439 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2440 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2441 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2442 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_TEXTURE);
2443 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_TEXTURE");
2444 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA);
2445 checkGLcall("GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA");
2446 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2447 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2449 case WINED3D_TOP_BLEND_FACTOR_ALPHA:
2450 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2451 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2452 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2453 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2454 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2455 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2456 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_CONSTANT);
2457 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_CONSTANT");
2458 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2459 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2460 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2461 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2462 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2463 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2464 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_CONSTANT);
2465 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_CONSTANT");
2466 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA);
2467 checkGLcall("GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA");
2468 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2469 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2471 case WINED3D_TOP_BLEND_TEXTURE_ALPHA_PM:
2472 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2473 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2474 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2475 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2476 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2477 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2478 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2479 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2480 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2481 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2482 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2483 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2484 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2485 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2486 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_TEXTURE);
2487 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_TEXTURE");
2488 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA);
2489 checkGLcall("GL_TEXTURE_ENV, opr3_target, GL_ONE_MINUS_SRC_ALPHA");
2490 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2491 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2493 case WINED3D_TOP_MODULATE_ALPHA_ADD_COLOR:
2494 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2495 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD"); /* Add = a0*a1 + a2*a3 */
2496 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1); /* a0 = src1/opr1 */
2497 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2498 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2499 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1"); /* a1 = 1 (see docs) */
2500 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2501 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2502 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2503 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2504 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2); /* a2 = arg2 */
2505 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2506 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2507 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2"); /* a3 = src1 alpha */
2508 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, src1);
2509 checkGLcall("GL_TEXTURE_ENV, src3_target, src1");
2511 case GL_SRC_COLOR: opr = GL_SRC_ALPHA; break;
2512 case GL_ONE_MINUS_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2514 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2515 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr");
2516 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2517 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2519 case WINED3D_TOP_MODULATE_COLOR_ADD_ALPHA:
2520 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2521 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2522 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2523 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2524 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2525 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2526 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2527 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2528 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2529 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2530 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src1);
2531 checkGLcall("GL_TEXTURE_ENV, src2_target, src1");
2533 case GL_SRC_COLOR: opr = GL_SRC_ALPHA; break;
2534 case GL_ONE_MINUS_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2536 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr);
2537 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr");
2538 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2539 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2540 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, invopr);
2541 checkGLcall("GL_TEXTURE_ENV, opr3_target, invopr");
2542 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2543 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2545 case WINED3D_TOP_MODULATE_INVALPHA_ADD_COLOR:
2546 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2547 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2548 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2549 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2550 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2551 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2552 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2553 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2554 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2555 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2556 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2557 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2558 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2559 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2560 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, src1);
2561 checkGLcall("GL_TEXTURE_ENV, src3_target, src1");
2563 case GL_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2564 case GL_ONE_MINUS_SRC_COLOR: opr = GL_SRC_ALPHA; break;
2565 case GL_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2566 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
2568 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr);
2569 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr");
2570 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2571 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2573 case WINED3D_TOP_MODULATE_INVCOLOR_ADD_ALPHA:
2574 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2575 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2576 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2577 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2579 case GL_SRC_COLOR: opr = GL_ONE_MINUS_SRC_COLOR; break;
2580 case GL_ONE_MINUS_SRC_COLOR: opr = GL_SRC_COLOR; break;
2581 case GL_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2582 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
2584 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr);
2585 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr");
2586 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2587 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2588 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2589 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2590 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src1);
2591 checkGLcall("GL_TEXTURE_ENV, src2_target, src1");
2593 case GL_SRC_COLOR: opr = GL_SRC_ALPHA; break;
2594 case GL_ONE_MINUS_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2596 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr);
2597 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr");
2598 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, GL_ZERO);
2599 checkGLcall("GL_TEXTURE_ENV, src3_target, GL_ZERO");
2600 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, invopr);
2601 checkGLcall("GL_TEXTURE_ENV, opr3_target, invopr");
2602 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2603 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2605 case WINED3D_TOP_MULTIPLY_ADD:
2606 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2607 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2608 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src3);
2609 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2610 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr3);
2611 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2612 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, GL_ZERO);
2613 checkGLcall("GL_TEXTURE_ENV, src1_target, GL_ZERO");
2614 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, invopr);
2615 checkGLcall("GL_TEXTURE_ENV, opr1_target, invopr");
2616 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src1);
2617 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2618 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr1);
2619 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2620 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src3_target, src2);
2621 checkGLcall("GL_TEXTURE_ENV, src3_target, src3");
2622 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr3_target, opr2);
2623 checkGLcall("GL_TEXTURE_ENV, opr3_target, opr3");
2624 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2625 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2628 case WINED3D_TOP_BUMPENVMAP:
2629 case WINED3D_TOP_BUMPENVMAP_LUMINANCE:
2630 FIXME("Implement bump environment mapping in GL_NV_texture_env_combine4 path\n");
2637 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE4_NV);
2638 checkGLcall("GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE4_NV");
2642 } /* GL_NV_texture_env_combine4 */
2644 Handled = TRUE; /* Again, assume handled */
2646 case WINED3D_TOP_DISABLE: /* Only for alpha */
2647 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_REPLACE);
2648 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_REPLACE");
2649 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, GL_PREVIOUS_EXT);
2650 checkGLcall("GL_TEXTURE_ENV, src0_target, GL_PREVIOUS_EXT");
2651 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, GL_SRC_ALPHA);
2652 checkGLcall("GL_TEXTURE_ENV, opr0_target, GL_SRC_ALPHA");
2653 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2654 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2656 case WINED3D_TOP_SELECT_ARG1:
2657 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_REPLACE);
2658 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_REPLACE");
2659 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2660 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2661 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2662 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2663 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2664 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2666 case WINED3D_TOP_SELECT_ARG2:
2667 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_REPLACE);
2668 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_REPLACE");
2669 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src2);
2670 checkGLcall("GL_TEXTURE_ENV, src0_target, src2");
2671 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr2);
2672 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr2");
2673 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2674 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2676 case WINED3D_TOP_MODULATE:
2677 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE);
2678 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE");
2679 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2680 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2681 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2682 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2683 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2684 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2685 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2686 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2687 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2688 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2690 case WINED3D_TOP_MODULATE_2X:
2691 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE);
2692 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE");
2693 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2694 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2695 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2696 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2697 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2698 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2699 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2700 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2701 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 2);
2702 checkGLcall("GL_TEXTURE_ENV, scal_target, 2");
2704 case WINED3D_TOP_MODULATE_4X:
2705 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE);
2706 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE");
2707 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2708 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2709 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2710 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2711 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2712 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2713 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2714 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2715 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 4);
2716 checkGLcall("GL_TEXTURE_ENV, scal_target, 4");
2718 case WINED3D_TOP_ADD:
2719 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD);
2720 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD");
2721 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2722 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2723 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2724 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2725 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2726 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2727 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2728 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2729 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2730 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2732 case WINED3D_TOP_ADD_SIGNED:
2733 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED);
2734 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED");
2735 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2736 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2737 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2738 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2739 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2740 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2741 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2742 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2743 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2744 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2746 case WINED3D_TOP_ADD_SIGNED_2X:
2747 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED);
2748 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_ADD_SIGNED");
2749 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2750 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2751 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2752 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2753 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2754 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2755 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2756 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2757 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 2);
2758 checkGLcall("GL_TEXTURE_ENV, scal_target, 2");
2760 case WINED3D_TOP_SUBTRACT:
2761 if (gl_info->supported[ARB_TEXTURE_ENV_COMBINE])
2763 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_SUBTRACT);
2764 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_SUBTRACT");
2765 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2766 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2767 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2768 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2769 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2770 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2771 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2772 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2773 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2774 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2776 FIXME("This version of opengl does not support GL_SUBTRACT\n");
2780 case WINED3D_TOP_BLEND_DIFFUSE_ALPHA:
2781 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE);
2782 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE");
2783 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2784 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2785 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2786 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2787 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2788 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2789 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2790 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2791 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_PRIMARY_COLOR);
2792 checkGLcall("GL_TEXTURE_ENV, src2_target, GL_PRIMARY_COLOR");
2793 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA);
2794 checkGLcall("GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA");
2795 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2796 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2798 case WINED3D_TOP_BLEND_TEXTURE_ALPHA:
2799 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE);
2800 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE");
2801 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2802 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2803 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2804 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2805 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2806 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2807 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2808 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2809 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_TEXTURE);
2810 checkGLcall("GL_TEXTURE_ENV, src2_target, GL_TEXTURE");
2811 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA);
2812 checkGLcall("GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA");
2813 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2814 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2816 case WINED3D_TOP_BLEND_FACTOR_ALPHA:
2817 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE);
2818 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE");
2819 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2820 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2821 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2822 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2823 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2824 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2825 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2826 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2827 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_CONSTANT);
2828 checkGLcall("GL_TEXTURE_ENV, src2_target, GL_CONSTANT");
2829 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA);
2830 checkGLcall("GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA");
2831 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2832 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2834 case WINED3D_TOP_BLEND_CURRENT_ALPHA:
2835 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE);
2836 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE");
2837 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2838 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2839 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2840 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2841 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2842 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2843 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2844 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2845 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, GL_PREVIOUS);
2846 checkGLcall("GL_TEXTURE_ENV, src2_target, GL_PREVIOUS");
2847 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA);
2848 checkGLcall("GL_TEXTURE_ENV, opr2_target, GL_SRC_ALPHA");
2849 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2850 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2852 case WINED3D_TOP_DOTPRODUCT3:
2853 if (gl_info->supported[ARB_TEXTURE_ENV_DOT3])
2855 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_DOT3_RGBA_ARB);
2856 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_DOT3_RGBA_ARB");
2858 else if (gl_info->supported[EXT_TEXTURE_ENV_DOT3])
2860 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_DOT3_RGBA_EXT);
2861 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_DOT3_RGBA_EXT");
2863 FIXME("This version of opengl does not support GL_DOT3\n");
2865 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2866 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2867 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2868 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2869 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2870 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2871 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2872 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2873 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2874 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2876 case WINED3D_TOP_LERP:
2877 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE);
2878 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_INTERPOLATE");
2879 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2880 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2881 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2882 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2883 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src2);
2884 checkGLcall("GL_TEXTURE_ENV, src1_target, src2");
2885 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr2);
2886 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr2");
2887 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src3);
2888 checkGLcall("GL_TEXTURE_ENV, src2_target, src3");
2889 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr3);
2890 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr3");
2891 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2892 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2894 case WINED3D_TOP_ADD_SMOOTH:
2895 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3])
2897 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI);
2898 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI");
2899 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2900 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2902 case GL_SRC_COLOR: opr = GL_ONE_MINUS_SRC_COLOR; break;
2903 case GL_ONE_MINUS_SRC_COLOR: opr = GL_SRC_COLOR; break;
2904 case GL_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2905 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
2907 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr);
2908 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr");
2909 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src1);
2910 checkGLcall("GL_TEXTURE_ENV, src1_target, src1");
2911 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr1);
2912 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr1");
2913 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2914 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2915 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2916 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2917 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2918 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2922 case WINED3D_TOP_BLEND_TEXTURE_ALPHA_PM:
2923 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3])
2925 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI);
2926 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI");
2927 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, GL_TEXTURE);
2928 checkGLcall("GL_TEXTURE_ENV, src0_target, GL_TEXTURE");
2929 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, GL_ONE_MINUS_SRC_ALPHA);
2930 checkGLcall("GL_TEXTURE_ENV, opr0_target, GL_ONE_MINUS_SRC_APHA");
2931 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src1);
2932 checkGLcall("GL_TEXTURE_ENV, src1_target, src1");
2933 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr1);
2934 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr1");
2935 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2936 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2937 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2938 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2939 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2940 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2944 case WINED3D_TOP_MODULATE_ALPHA_ADD_COLOR:
2945 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3])
2947 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI);
2948 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI");
2949 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2950 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2952 case GL_SRC_COLOR: opr = GL_SRC_ALPHA; break;
2953 case GL_ONE_MINUS_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2954 case GL_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
2955 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2957 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr);
2958 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr");
2959 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src1);
2960 checkGLcall("GL_TEXTURE_ENV, src1_target, src1");
2961 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr1);
2962 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr1");
2963 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2964 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2965 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2966 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2967 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2968 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
2972 case WINED3D_TOP_MODULATE_COLOR_ADD_ALPHA:
2973 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3])
2975 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI);
2976 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI");
2977 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
2978 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
2979 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
2980 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
2981 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src1);
2982 checkGLcall("GL_TEXTURE_ENV, src1_target, src1");
2984 case GL_SRC_COLOR: opr = GL_SRC_ALPHA; break;
2985 case GL_ONE_MINUS_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2986 case GL_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
2987 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
2989 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr);
2990 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr");
2991 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
2992 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
2993 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
2994 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
2995 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
2996 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
3000 case WINED3D_TOP_MODULATE_INVALPHA_ADD_COLOR:
3001 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3])
3003 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI);
3004 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI");
3005 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
3006 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
3008 case GL_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
3009 case GL_ONE_MINUS_SRC_COLOR: opr = GL_SRC_ALPHA; break;
3010 case GL_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
3011 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
3013 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr);
3014 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr");
3015 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src1);
3016 checkGLcall("GL_TEXTURE_ENV, src1_target, src1");
3017 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr1);
3018 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr1");
3019 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
3020 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
3021 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
3022 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
3023 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
3024 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
3028 case WINED3D_TOP_MODULATE_INVCOLOR_ADD_ALPHA:
3029 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3])
3031 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI);
3032 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI");
3033 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
3034 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
3036 case GL_SRC_COLOR: opr = GL_ONE_MINUS_SRC_COLOR; break;
3037 case GL_ONE_MINUS_SRC_COLOR: opr = GL_SRC_COLOR; break;
3038 case GL_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
3039 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
3041 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr);
3042 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr");
3043 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src1);
3044 checkGLcall("GL_TEXTURE_ENV, src1_target, src1");
3046 case GL_SRC_COLOR: opr = GL_SRC_ALPHA; break;
3047 case GL_ONE_MINUS_SRC_COLOR: opr = GL_ONE_MINUS_SRC_ALPHA; break;
3048 case GL_SRC_ALPHA: opr = GL_SRC_ALPHA; break;
3049 case GL_ONE_MINUS_SRC_ALPHA: opr = GL_ONE_MINUS_SRC_ALPHA; break;
3051 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr);
3052 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr");
3053 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
3054 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
3055 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
3056 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
3057 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
3058 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
3062 case WINED3D_TOP_MULTIPLY_ADD:
3063 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3])
3065 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI);
3066 checkGLcall("GL_TEXTURE_ENV, comb_target, GL_MODULATE_ADD_ATI");
3067 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src0_target, src1);
3068 checkGLcall("GL_TEXTURE_ENV, src0_target, src1");
3069 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr0_target, opr1);
3070 checkGLcall("GL_TEXTURE_ENV, opr0_target, opr1");
3071 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src1_target, src3);
3072 checkGLcall("GL_TEXTURE_ENV, src1_target, src3");
3073 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr1_target, opr3);
3074 checkGLcall("GL_TEXTURE_ENV, opr1_target, opr3");
3075 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, src2_target, src2);
3076 checkGLcall("GL_TEXTURE_ENV, src2_target, src2");
3077 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, opr2_target, opr2);
3078 checkGLcall("GL_TEXTURE_ENV, opr2_target, opr2");
3079 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, scal_target, 1);
3080 checkGLcall("GL_TEXTURE_ENV, scal_target, 1");
3084 case WINED3D_TOP_BUMPENVMAP_LUMINANCE:
3085 case WINED3D_TOP_BUMPENVMAP:
3086 if (gl_info->supported[NV_TEXTURE_SHADER2])
3088 /* Technically texture shader support without register combiners is possible, but not expected to occur
3089 * on real world cards, so for now a fixme should be enough
3091 FIXME("Implement bump mapping with GL_NV_texture_shader in non register combiner path\n");
3098 BOOL combineOK = TRUE;
3099 if (gl_info->supported[NV_TEXTURE_ENV_COMBINE4])
3104 op2 = state->texture_states[Stage][WINED3D_TSS_COLOR_OP];
3106 op2 = state->texture_states[Stage][WINED3D_TSS_ALPHA_OP];
3108 /* Note: If COMBINE4 in effect can't go back to combine! */
3111 case WINED3D_TOP_ADD_SMOOTH:
3112 case WINED3D_TOP_BLEND_TEXTURE_ALPHA_PM:
3113 case WINED3D_TOP_MODULATE_ALPHA_ADD_COLOR:
3114 case WINED3D_TOP_MODULATE_COLOR_ADD_ALPHA:
3115 case WINED3D_TOP_MODULATE_INVALPHA_ADD_COLOR:
3116 case WINED3D_TOP_MODULATE_INVCOLOR_ADD_ALPHA:
3117 case WINED3D_TOP_MULTIPLY_ADD:
3118 /* Ignore those implemented in both cases */
3121 case WINED3D_TOP_SELECT_ARG1:
3122 case WINED3D_TOP_SELECT_ARG2:
3127 FIXME("Can't use COMBINE4 and COMBINE together, thisop=%s, otherop=%s, isAlpha(%d)\n", debug_d3dtop(op), debug_d3dtop(op2), isAlpha);
3135 gl_info->gl_ops.gl.p_glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
3136 checkGLcall("GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE");
3142 /* After all the extensions, if still unhandled, report fixme */
3143 FIXME("Unhandled texture operation %s\n", debug_d3dtop(op));
3147 static void tex_colorop(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3149 DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
3150 const struct wined3d_device *device = context->swapchain->device;
3151 BOOL tex_used = device->fixed_function_usage_map & (1 << stage);
3152 DWORD mapped_stage = device->texUnitMap[stage];
3153 const struct wined3d_gl_info *gl_info = context->gl_info;
3155 TRACE("Setting color op for stage %d\n", stage);
3157 /* Using a pixel shader? Don't care for anything here, the shader applying does it */
3158 if (use_ps(state)) return;
3160 if (stage != mapped_stage) WARN("Using non 1:1 mapping: %d -> %d!\n", stage, mapped_stage);
3162 if (mapped_stage != WINED3D_UNMAPPED_STAGE)
3164 if (tex_used && mapped_stage >= gl_info->limits.textures)
3166 FIXME("Attempt to enable unsupported stage!\n");
3169 context_active_texture(context, gl_info, mapped_stage);
3172 if (stage >= state->lowest_disabled_stage)
3174 TRACE("Stage disabled\n");
3175 if (mapped_stage != WINED3D_UNMAPPED_STAGE)
3177 /* Disable everything here */
3178 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_2D);
3179 checkGLcall("glDisable(GL_TEXTURE_2D)");
3180 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_3D);
3181 checkGLcall("glDisable(GL_TEXTURE_3D)");
3182 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
3184 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_CUBE_MAP_ARB);
3185 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
3187 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
3189 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_RECTANGLE_ARB);
3190 checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
3197 /* The sampler will also activate the correct texture dimensions, so no
3198 * need to do it here if the sampler for this stage is dirty. */
3199 if (!isStateDirty(context, STATE_SAMPLER(stage)) && tex_used)
3200 texture_activate_dimensions(state->textures[stage], gl_info);
3202 set_tex_op(gl_info, state, FALSE, stage,
3203 state->texture_states[stage][WINED3D_TSS_COLOR_OP],
3204 state->texture_states[stage][WINED3D_TSS_COLOR_ARG1],
3205 state->texture_states[stage][WINED3D_TSS_COLOR_ARG2],
3206 state->texture_states[stage][WINED3D_TSS_COLOR_ARG0]);
3209 void tex_alphaop(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3211 DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
3212 const struct wined3d_device *device = context->swapchain->device;
3213 BOOL tex_used = device->fixed_function_usage_map & (1 << stage);
3214 DWORD mapped_stage = device->texUnitMap[stage];
3215 const struct wined3d_gl_info *gl_info = context->gl_info;
3216 DWORD op, arg1, arg2, arg0;
3218 TRACE("Setting alpha op for stage %d\n", stage);
3219 /* Do not care for enabled / disabled stages, just assign the settings. colorop disables / enables required stuff */
3220 if (mapped_stage != WINED3D_UNMAPPED_STAGE)
3222 if (tex_used && mapped_stage >= gl_info->limits.textures)
3224 FIXME("Attempt to enable unsupported stage!\n");
3227 context_active_texture(context, gl_info, mapped_stage);
3230 op = state->texture_states[stage][WINED3D_TSS_ALPHA_OP];
3231 arg1 = state->texture_states[stage][WINED3D_TSS_ALPHA_ARG1];
3232 arg2 = state->texture_states[stage][WINED3D_TSS_ALPHA_ARG2];
3233 arg0 = state->texture_states[stage][WINED3D_TSS_ALPHA_ARG0];
3235 if (state->render_states[WINED3D_RS_COLORKEYENABLE] && !stage && state->textures[0])
3237 struct wined3d_texture *texture = state->textures[0];
3238 GLenum texture_dimensions = texture->target;
3240 if (texture_dimensions == GL_TEXTURE_2D || texture_dimensions == GL_TEXTURE_RECTANGLE_ARB)
3242 struct wined3d_surface *surf = surface_from_resource(texture->sub_resources[0]);
3244 if (surf->CKeyFlags & WINEDDSD_CKSRCBLT && !surf->resource.format->alpha_size)
3246 /* Color keying needs to pass alpha values from the texture through to have the alpha test work
3247 * properly. On the other hand applications can still use texture combiners apparently. This code
3248 * takes care that apps cannot remove the texture's alpha channel entirely.
3250 * The fixup is required for Prince of Persia 3D(prison bars), while Moto racer 2 requires
3251 * D3DTOP_MODULATE to work on color keyed surfaces. Aliens vs Predator 1 uses color keyed textures
3252 * and alpha component of diffuse color to draw things like translucent text and perform other
3255 * Aliens vs Predator 1 relies on diffuse alpha having an effect, so it cannot be ignored. To
3256 * provide the behavior expected by the game, while emulating the colorkey, diffuse alpha must be
3257 * modulated with texture alpha. OTOH, Moto racer 2 at some points sets alphaop/alphaarg to
3258 * SELECTARG/CURRENT, yet puts garbage in diffuse alpha (zeroes). This works on native, because the
3259 * game disables alpha test and alpha blending. Alpha test is overwritten by wine's for purposes of
3260 * color-keying though, so this will lead to missing geometry if texture alpha is modulated (pixels
3261 * fail alpha test). To get around this, ALPHABLENDENABLE state is checked: if the app enables alpha
3262 * blending, it can be expected to provide meaningful values in diffuse alpha, so it should be
3263 * modulated with texture alpha; otherwise, selecting diffuse alpha is ignored in favour of texture
3266 * What to do with multitexturing? So far no app has been found that uses color keying with
3268 if (op == WINED3D_TOP_DISABLE)
3270 arg1 = WINED3DTA_TEXTURE;
3271 op = WINED3D_TOP_SELECT_ARG1;
3273 else if (op == WINED3D_TOP_SELECT_ARG1 && arg1 != WINED3DTA_TEXTURE)
3275 if (state->render_states[WINED3D_RS_ALPHABLENDENABLE])
3277 arg2 = WINED3DTA_TEXTURE;
3278 op = WINED3D_TOP_MODULATE;
3280 else arg1 = WINED3DTA_TEXTURE;
3282 else if (op == WINED3D_TOP_SELECT_ARG2 && arg2 != WINED3DTA_TEXTURE)
3284 if (state->render_states[WINED3D_RS_ALPHABLENDENABLE])
3286 arg1 = WINED3DTA_TEXTURE;
3287 op = WINED3D_TOP_MODULATE;
3289 else arg2 = WINED3DTA_TEXTURE;
3295 /* tex_alphaop is shared between the ffp and nvrc because the difference only comes down to
3296 * this if block here, and the other code(color keying, texture unit selection) are the same
3298 TRACE("Setting alpha op for stage %d\n", stage);
3299 if (gl_info->supported[NV_REGISTER_COMBINERS])
3301 set_tex_op_nvrc(gl_info, state, TRUE, stage, op, arg1, arg2, arg0,
3302 mapped_stage, state->texture_states[stage][WINED3D_TSS_RESULT_ARG]);
3306 set_tex_op(gl_info, state, TRUE, stage, op, arg1, arg2, arg0);
3310 static void transform_texture(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3312 DWORD texUnit = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
3313 const struct wined3d_device *device = context->swapchain->device;
3314 const struct wined3d_gl_info *gl_info = context->gl_info;
3315 DWORD mapped_stage = device->texUnitMap[texUnit];
3319 /* Ignore this when a vertex shader is used, or if the streams aren't sorted out yet */
3320 if (use_vs(state) || isStateDirty(context, STATE_VDECL))
3322 TRACE("Using a vertex shader, or stream sources not sorted out yet, skipping\n");
3326 if (mapped_stage == WINED3D_UNMAPPED_STAGE) return;
3327 if (mapped_stage >= gl_info->limits.textures) return;
3329 context_active_texture(context, gl_info, mapped_stage);
3330 generated = (state->texture_states[texUnit][WINED3D_TSS_TEXCOORD_INDEX] & 0xffff0000) != WINED3DTSS_TCI_PASSTHRU;
3331 coordIdx = min(state->texture_states[texUnit][WINED3D_TSS_TEXCOORD_INDEX & 0x0000ffff], MAX_TEXTURES - 1);
3333 set_texture_matrix(gl_info, &state->transforms[WINED3D_TS_TEXTURE0 + texUnit].u.m[0][0],
3334 state->texture_states[texUnit][WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS],
3335 generated, context->last_was_rhw,
3336 device->strided_streams.use_map & (1 << (WINED3D_FFP_TEXCOORD0 + coordIdx))
3337 ? device->strided_streams.elements[WINED3D_FFP_TEXCOORD0 + coordIdx].format->id
3338 : WINED3DFMT_UNKNOWN,
3339 device->shader_backend->shader_has_ffp_proj_control(device->shader_priv));
3341 /* The sampler applying function calls us if this changes */
3342 if ((context->lastWasPow2Texture & (1 << texUnit)) && state->textures[texUnit])
3345 FIXME("Non-power2 texture being used with generated texture coords\n");
3347 /* NP2 texcoord fixup is implemented for pixelshaders so only enable the
3348 fixed-function-pipeline fixup via pow2Matrix when no PS is used. */
3351 TRACE("Non power two matrix multiply fixup\n");
3352 gl_info->gl_ops.gl.p_glMultMatrixf(state->textures[texUnit]->pow2_matrix);
3357 static void unload_tex_coords(const struct wined3d_gl_info *gl_info)
3359 unsigned int texture_idx;
3361 for (texture_idx = 0; texture_idx < gl_info->limits.texture_coords; ++texture_idx)
3363 GL_EXTCALL(glClientActiveTextureARB(GL_TEXTURE0_ARB + texture_idx));
3364 gl_info->gl_ops.gl.p_glDisableClientState(GL_TEXTURE_COORD_ARRAY);
3368 static void load_tex_coords(const struct wined3d_context *context, const struct wined3d_stream_info *si,
3369 GLuint *curVBO, const struct wined3d_state *state)
3371 const struct wined3d_device *device = context->swapchain->device;
3372 const struct wined3d_gl_info *gl_info = context->gl_info;
3373 unsigned int mapped_stage = 0;
3374 unsigned int textureNo = 0;
3376 for (textureNo = 0; textureNo < gl_info->limits.texture_stages; ++textureNo)
3378 int coordIdx = state->texture_states[textureNo][WINED3D_TSS_TEXCOORD_INDEX];
3380 mapped_stage = device->texUnitMap[textureNo];
3381 if (mapped_stage == WINED3D_UNMAPPED_STAGE) continue;
3383 if (mapped_stage >= gl_info->limits.texture_coords)
3385 FIXME("Attempted to load unsupported texture coordinate %u\n", mapped_stage);
3389 if (coordIdx < MAX_TEXTURES && (si->use_map & (1 << (WINED3D_FFP_TEXCOORD0 + coordIdx))))
3391 const struct wined3d_stream_info_element *e = &si->elements[WINED3D_FFP_TEXCOORD0 + coordIdx];
3393 TRACE("Setting up texture %u, idx %d, coordindx %u, data {%#x:%p}.\n",
3394 textureNo, mapped_stage, coordIdx, e->data.buffer_object, e->data.addr);
3396 if (*curVBO != e->data.buffer_object)
3398 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->data.buffer_object));
3399 checkGLcall("glBindBufferARB");
3400 *curVBO = e->data.buffer_object;
3403 GL_EXTCALL(glClientActiveTextureARB(GL_TEXTURE0_ARB + mapped_stage));
3404 checkGLcall("glClientActiveTextureARB");
3406 /* The coords to supply depend completely on the fvf / vertex shader */
3407 gl_info->gl_ops.gl.p_glTexCoordPointer(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
3408 e->data.addr + state->load_base_vertex_index * e->stride);
3409 gl_info->gl_ops.gl.p_glEnableClientState(GL_TEXTURE_COORD_ARRAY);
3413 GL_EXTCALL(glMultiTexCoord4fARB(GL_TEXTURE0_ARB + mapped_stage, 0, 0, 0, 1));
3416 if (gl_info->supported[NV_REGISTER_COMBINERS])
3418 /* The number of the mapped stages increases monotonically, so it's fine to use the last used one. */
3419 for (textureNo = mapped_stage + 1; textureNo < gl_info->limits.textures; ++textureNo)
3421 GL_EXTCALL(glMultiTexCoord4fARB(GL_TEXTURE0_ARB + textureNo, 0, 0, 0, 1));
3425 checkGLcall("loadTexCoords");
3428 static void tex_coordindex(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3430 DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
3431 const struct wined3d_device *device = context->swapchain->device;
3432 static const GLfloat s_plane[] = { 1.0f, 0.0f, 0.0f, 0.0f };
3433 static const GLfloat t_plane[] = { 0.0f, 1.0f, 0.0f, 0.0f };
3434 static const GLfloat r_plane[] = { 0.0f, 0.0f, 1.0f, 0.0f };
3435 static const GLfloat q_plane[] = { 0.0f, 0.0f, 0.0f, 1.0f };
3436 const struct wined3d_gl_info *gl_info = context->gl_info;
3437 DWORD mapped_stage = device->texUnitMap[stage];
3439 if (mapped_stage == WINED3D_UNMAPPED_STAGE)
3441 TRACE("No texture unit mapped to stage %d. Skipping texture coordinates.\n", stage);
3445 if (mapped_stage >= gl_info->limits.fragment_samplers)
3447 WARN("stage %u not mapped to a valid texture unit (%u)\n", stage, mapped_stage);
3450 context_active_texture(context, gl_info, mapped_stage);
3452 /* Values 0-7 are indexes into the FVF tex coords - See comments in DrawPrimitive
3454 * FIXME: When using generated texture coordinates, the index value is used to specify the wrapping mode.
3455 * eg. SetTextureStageState( 0, WINED3D_TSS_TEXCOORDINDEX, WINED3D_TSS_TCI_CAMERASPACEPOSITION | 1 );
3456 * means use the vertex position (camera-space) as the input texture coordinates
3457 * for this texture stage, and the wrap mode set in the WINED3D_RS_WRAP1 render
3458 * state. We do not (yet) support the WINED3DRENDERSTATE_WRAPx values, nor tie them up
3459 * to the TEXCOORDINDEX value
3461 switch (state->texture_states[stage][WINED3D_TSS_TEXCOORD_INDEX] & 0xffff0000)
3463 case WINED3DTSS_TCI_PASSTHRU:
3464 /* Use the specified texture coordinates contained within the
3465 * vertex format. This value resolves to zero. */
3466 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_S);
3467 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_T);
3468 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_R);
3469 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_Q);
3470 checkGLcall("WINED3DTSS_TCI_PASSTHRU - Disable texgen.");
3473 case WINED3DTSS_TCI_CAMERASPACEPOSITION:
3474 /* CameraSpacePosition means use the vertex position, transformed to camera space,
3475 * as the input texture coordinates for this stage's texture transformation. This
3476 * equates roughly to EYE_LINEAR */
3478 gl_info->gl_ops.gl.p_glMatrixMode(GL_MODELVIEW);
3479 gl_info->gl_ops.gl.p_glPushMatrix();
3480 gl_info->gl_ops.gl.p_glLoadIdentity();
3481 gl_info->gl_ops.gl.p_glTexGenfv(GL_S, GL_EYE_PLANE, s_plane);
3482 gl_info->gl_ops.gl.p_glTexGenfv(GL_T, GL_EYE_PLANE, t_plane);
3483 gl_info->gl_ops.gl.p_glTexGenfv(GL_R, GL_EYE_PLANE, r_plane);
3484 gl_info->gl_ops.gl.p_glTexGenfv(GL_Q, GL_EYE_PLANE, q_plane);
3485 gl_info->gl_ops.gl.p_glPopMatrix();
3486 checkGLcall("WINED3DTSS_TCI_CAMERASPACEPOSITION - Set eye plane.");
3488 gl_info->gl_ops.gl.p_glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR);
3489 gl_info->gl_ops.gl.p_glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR);
3490 gl_info->gl_ops.gl.p_glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_EYE_LINEAR);
3491 checkGLcall("WINED3DTSS_TCI_CAMERASPACEPOSITION - Set texgen mode.");
3493 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_S);
3494 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_T);
3495 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_R);
3496 checkGLcall("WINED3DTSS_TCI_CAMERASPACEPOSITION - Enable texgen.");
3500 case WINED3DTSS_TCI_CAMERASPACENORMAL:
3501 /* Note that NV_TEXGEN_REFLECTION support is implied when
3502 * ARB_TEXTURE_CUBE_MAP is supported */
3503 if (!gl_info->supported[NV_TEXGEN_REFLECTION])
3505 FIXME("WINED3DTSS_TCI_CAMERASPACENORMAL not supported.\n");
3509 gl_info->gl_ops.gl.p_glMatrixMode(GL_MODELVIEW);
3510 gl_info->gl_ops.gl.p_glPushMatrix();
3511 gl_info->gl_ops.gl.p_glLoadIdentity();
3512 gl_info->gl_ops.gl.p_glTexGenfv(GL_S, GL_EYE_PLANE, s_plane);
3513 gl_info->gl_ops.gl.p_glTexGenfv(GL_T, GL_EYE_PLANE, t_plane);
3514 gl_info->gl_ops.gl.p_glTexGenfv(GL_R, GL_EYE_PLANE, r_plane);
3515 gl_info->gl_ops.gl.p_glTexGenfv(GL_Q, GL_EYE_PLANE, q_plane);
3516 gl_info->gl_ops.gl.p_glPopMatrix();
3517 checkGLcall("WINED3DTSS_TCI_CAMERASPACENORMAL - Set eye plane.");
3519 gl_info->gl_ops.gl.p_glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
3520 gl_info->gl_ops.gl.p_glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
3521 gl_info->gl_ops.gl.p_glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
3522 checkGLcall("WINED3DTSS_TCI_CAMERASPACENORMAL - Set texgen mode.");
3524 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_S);
3525 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_T);
3526 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_R);
3527 checkGLcall("WINED3DTSS_TCI_CAMERASPACENORMAL - Enable texgen.");
3531 case WINED3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR:
3532 /* Note that NV_TEXGEN_REFLECTION support is implied when
3533 * ARB_TEXTURE_CUBE_MAP is supported */
3534 if (!gl_info->supported[NV_TEXGEN_REFLECTION])
3536 FIXME("WINED3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR not supported.\n");
3540 gl_info->gl_ops.gl.p_glMatrixMode(GL_MODELVIEW);
3541 gl_info->gl_ops.gl.p_glPushMatrix();
3542 gl_info->gl_ops.gl.p_glLoadIdentity();
3543 gl_info->gl_ops.gl.p_glTexGenfv(GL_S, GL_EYE_PLANE, s_plane);
3544 gl_info->gl_ops.gl.p_glTexGenfv(GL_T, GL_EYE_PLANE, t_plane);
3545 gl_info->gl_ops.gl.p_glTexGenfv(GL_R, GL_EYE_PLANE, r_plane);
3546 gl_info->gl_ops.gl.p_glTexGenfv(GL_Q, GL_EYE_PLANE, q_plane);
3547 gl_info->gl_ops.gl.p_glPopMatrix();
3548 checkGLcall("WINED3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR - Set eye plane.");
3550 gl_info->gl_ops.gl.p_glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV);
3551 gl_info->gl_ops.gl.p_glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV);
3552 gl_info->gl_ops.gl.p_glTexGeni(GL_R, GL_TEXTURE_GEN_MODE, GL_REFLECTION_MAP_NV);
3553 checkGLcall("WINED3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR - Set texgen mode.");
3555 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_S);
3556 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_T);
3557 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_R);
3558 checkGLcall("WINED3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR - Enable texgen.");
3562 case WINED3DTSS_TCI_SPHEREMAP:
3563 gl_info->gl_ops.gl.p_glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
3564 gl_info->gl_ops.gl.p_glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
3565 checkGLcall("WINED3DTSS_TCI_SPHEREMAP - Set texgen mode.");
3567 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_S);
3568 gl_info->gl_ops.gl.p_glEnable(GL_TEXTURE_GEN_T);
3569 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_R);
3570 checkGLcall("WINED3DTSS_TCI_SPHEREMAP - Enable texgen.");
3575 FIXME("Unhandled WINED3D_TSS_TEXCOORD_INDEX %#x.\n",
3576 state->texture_states[stage][WINED3D_TSS_TEXCOORD_INDEX]);
3577 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_S);
3578 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_T);
3579 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_R);
3580 gl_info->gl_ops.gl.p_glDisable(GL_TEXTURE_GEN_Q);
3581 checkGLcall("Disable texgen.");
3586 /* Update the texture matrix. */
3587 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_TEXTURE0 + stage)))
3588 transform_texture(context, state, STATE_TEXTURESTAGE(stage, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS));
3590 if (!isStateDirty(context, STATE_VDECL) && context->namedArraysLoaded)
3592 /* Reload the arrays if we are using fixed function arrays to reflect the selected coord input
3593 * source. Call loadTexCoords directly because there is no need to reparse the vertex declaration
3594 * and do all the things linked to it
3595 * TODO: Tidy that up to reload only the arrays of the changed unit
3597 GLuint curVBO = gl_info->supported[ARB_VERTEX_BUFFER_OBJECT] ? ~0U : 0;
3599 unload_tex_coords(gl_info);
3600 load_tex_coords(context, &device->strided_streams, &curVBO, state);
3604 static void tex_bumpenvlscale(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3606 DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
3607 const struct wined3d_shader *ps = state->pixel_shader;
3609 /* The pixel shader has to know the luminance scale. Do a constants update. */
3610 if (ps && stage && (ps->reg_maps.luminanceparams & (1 << stage)))
3611 context->load_constants = 1;
3614 static void sampler_texmatrix(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3616 const DWORD sampler = state_id - STATE_SAMPLER(0);
3617 const struct wined3d_texture *texture = state->textures[sampler];
3619 TRACE("context %p, state %p, state_id %#x.\n", context, state, state_id);
3621 if(!texture) return;
3622 /* The fixed function np2 texture emulation uses the texture matrix to fix up the coordinates
3623 * wined3d_texture_apply_state_changes() multiplies the set matrix with a fixup matrix. Before the
3624 * scaling is reapplied or removed, the texture matrix has to be reapplied
3626 * The mapped stage is already active because the sampler() function below, which is part of the
3629 if (sampler < MAX_TEXTURES)
3631 const BOOL texIsPow2 = !(texture->flags & WINED3D_TEXTURE_POW2_MAT_IDENT);
3633 if (texIsPow2 || (context->lastWasPow2Texture & (1 << sampler)))
3635 const struct wined3d_device *device = context->swapchain->device;
3638 context->lastWasPow2Texture |= 1 << sampler;
3640 context->lastWasPow2Texture &= ~(1 << sampler);
3642 transform_texture(context, state,
3643 STATE_TEXTURESTAGE(device->texUnitMap[sampler], WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS));
3648 static void sampler(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3650 const struct wined3d_device *device = context->swapchain->device;
3651 DWORD sampler = state_id - STATE_SAMPLER(0);
3652 DWORD mapped_stage = device->texUnitMap[sampler];
3653 const struct wined3d_gl_info *gl_info = context->gl_info;
3659 TRACE("Sampler: %d\n", sampler);
3660 /* Enabling and disabling texture dimensions is done by texture stage state / pixel shader setup, this function
3661 * only has to bind textures and set the per texture states
3664 if (mapped_stage == WINED3D_UNMAPPED_STAGE)
3666 TRACE("No sampler mapped to stage %d. Returning.\n", sampler);
3670 if (mapped_stage >= gl_info->limits.combined_samplers)
3674 context_active_texture(context, gl_info, mapped_stage);
3676 if (state->textures[sampler])
3678 struct wined3d_texture *texture = state->textures[sampler];
3679 BOOL srgb = state->sampler_states[sampler][WINED3D_SAMP_SRGB_TEXTURE];
3681 texture->texture_ops->texture_bind(texture, context, srgb);
3682 wined3d_texture_apply_state_changes(texture, state->sampler_states[sampler], gl_info);
3684 if (gl_info->supported[EXT_TEXTURE_LOD_BIAS])
3686 tmpvalue.d = state->sampler_states[sampler][WINED3D_SAMP_MIPMAP_LOD_BIAS];
3687 gl_info->gl_ops.gl.p_glTexEnvf(GL_TEXTURE_FILTER_CONTROL_EXT,
3688 GL_TEXTURE_LOD_BIAS_EXT, tmpvalue.f);
3689 checkGLcall("glTexEnvf(GL_TEXTURE_LOD_BIAS_EXT, ...)");
3692 if (!use_ps(state) && sampler < state->lowest_disabled_stage)
3694 if (state->render_states[WINED3D_RS_COLORKEYENABLE] && !sampler)
3696 /* If color keying is enabled update the alpha test, it
3697 * depends on the existence of a color key in stage 0. */
3698 state_alpha(context, state, WINED3D_RS_COLORKEYENABLE);
3702 /* Trigger shader constant reloading (for NP2 texcoord fixup) */
3703 if (!(texture->flags & WINED3D_TEXTURE_POW2_MAT_IDENT))
3704 device->shader_backend->shader_load_np2fixup_constants(device->shader_priv, gl_info, state);
3708 if (sampler < state->lowest_disabled_stage)
3710 /* TODO: What should I do with pixel shaders here ??? */
3711 if (state->render_states[WINED3D_RS_COLORKEYENABLE] && !sampler)
3713 /* If color keying is enabled update the alpha test, it
3714 * depends on the existence of a color key in stage 0. */
3715 state_alpha(context, state, WINED3D_RS_COLORKEYENABLE);
3717 } /* Otherwise tex_colorop disables the stage */
3718 context_bind_texture(context, GL_NONE, 0);
3722 void apply_pixelshader(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3728 if (!context->last_was_pshader)
3730 /* Former draw without a pixel shader, some samplers may be
3731 * disabled because of WINED3D_TSS_COLOR_OP = WINED3DTOP_DISABLE
3732 * make sure to enable them. */
3733 for (i = 0; i < MAX_FRAGMENT_SAMPLERS; ++i)
3735 if (!isStateDirty(context, STATE_SAMPLER(i)))
3736 sampler(context, state, STATE_SAMPLER(i));
3738 context->last_was_pshader = TRUE;
3742 /* Otherwise all samplers were activated by the code above in
3743 * earlier draws, or by sampler() if a different texture was
3744 * bound. I don't have to do anything. */
3749 /* Disabled the pixel shader - color ops weren't applied while it was
3750 * enabled, so re-apply them. */
3751 for (i = 0; i < context->gl_info->limits.texture_stages; ++i)
3753 if (!isStateDirty(context, STATE_TEXTURESTAGE(i, WINED3D_TSS_COLOR_OP)))
3754 context_apply_state(context, state, STATE_TEXTURESTAGE(i, WINED3D_TSS_COLOR_OP));
3756 context->last_was_pshader = FALSE;
3759 context->select_shader = 1;
3760 context->load_constants = 1;
3763 static void state_geometry_shader(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3765 context->select_shader = 1;
3768 static void shader_bumpenvmat(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3770 DWORD stage = (state_id - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
3771 const struct wined3d_shader *ps = state->pixel_shader;
3773 /* The pixel shader has to know the bump env matrix. Do a constants update. */
3774 if (ps && stage && (ps->reg_maps.bumpmat & (1 << stage)))
3775 context->load_constants = 1;
3778 static void transform_world(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3780 const struct wined3d_gl_info *gl_info = context->gl_info;
3782 /* This function is called by transform_view below if the view matrix was changed too
3784 * Deliberately no check if the vertex declaration is dirty because the vdecl state
3785 * does not always update the world matrix, only on a switch between transformed
3786 * and untransformed draws. It *may* happen that the world matrix is set 2 times during one
3787 * draw, but that should be rather rare and cheaper in total.
3789 gl_info->gl_ops.gl.p_glMatrixMode(GL_MODELVIEW);
3790 checkGLcall("glMatrixMode");
3792 if (context->last_was_rhw)
3794 gl_info->gl_ops.gl.p_glLoadIdentity();
3795 checkGLcall("glLoadIdentity()");
3799 /* In the general case, the view matrix is the identity matrix */
3800 if (context->swapchain->device->view_ident)
3802 gl_info->gl_ops.gl.p_glLoadMatrixf(&state->transforms[WINED3D_TS_WORLD_MATRIX(0)].u.m[0][0]);
3803 checkGLcall("glLoadMatrixf");
3807 gl_info->gl_ops.gl.p_glLoadMatrixf(&state->transforms[WINED3D_TS_VIEW].u.m[0][0]);
3808 checkGLcall("glLoadMatrixf");
3809 gl_info->gl_ops.gl.p_glMultMatrixf(&state->transforms[WINED3D_TS_WORLD_MATRIX(0)].u.m[0][0]);
3810 checkGLcall("glMultMatrixf");
3815 static void clipplane(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3817 const struct wined3d_gl_info *gl_info = context->gl_info;
3818 UINT index = state_id - STATE_CLIPPLANE(0);
3821 if (isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_VIEW)) || index >= gl_info->limits.clipplanes)
3824 gl_info->gl_ops.gl.p_glMatrixMode(GL_MODELVIEW);
3825 gl_info->gl_ops.gl.p_glPushMatrix();
3827 /* Clip Plane settings are affected by the model view in OpenGL, the View transform in direct3d */
3829 gl_info->gl_ops.gl.p_glLoadMatrixf(&state->transforms[WINED3D_TS_VIEW].u.m[0][0]);
3831 /* With vertex shaders, clip planes are not transformed in Direct3D,
3832 * while in OpenGL they are still transformed by the model view matix. */
3833 gl_info->gl_ops.gl.p_glLoadIdentity();
3835 plane[0] = state->clip_planes[index].x;
3836 plane[1] = state->clip_planes[index].y;
3837 plane[2] = state->clip_planes[index].z;
3838 plane[3] = state->clip_planes[index].w;
3840 TRACE("Clipplane [%.8e, %.8e, %.8e, %.8e]\n",
3841 plane[0], plane[1], plane[2], plane[3]);
3842 gl_info->gl_ops.gl.p_glClipPlane(GL_CLIP_PLANE0 + index, plane);
3843 checkGLcall("glClipPlane");
3845 gl_info->gl_ops.gl.p_glPopMatrix();
3848 static void transform_worldex(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3850 UINT matrix = state_id - STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(0));
3851 const struct wined3d_gl_info *gl_info = context->gl_info;
3854 TRACE("Setting world matrix %d\n", matrix);
3856 if (matrix >= gl_info->limits.blends)
3858 WARN("Unsupported blend matrix set\n");
3862 if (isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_VIEW)))
3865 /* GL_MODELVIEW0_ARB: 0x1700
3866 * GL_MODELVIEW1_ARB: 0x850a
3867 * GL_MODELVIEW2_ARB: 0x8722
3868 * GL_MODELVIEW3_ARB: 0x8723
3870 * GL_MODELVIEW31_ARB: 0x873f
3872 if(matrix == 1) glMat = GL_MODELVIEW1_ARB;
3873 else glMat = GL_MODELVIEW2_ARB - 2 + matrix;
3875 gl_info->gl_ops.gl.p_glMatrixMode(glMat);
3876 checkGLcall("glMatrixMode(glMat)");
3878 /* World matrix 0 is multiplied with the view matrix because d3d uses 3
3879 * matrices while gl uses only 2. To avoid weighting the view matrix
3880 * incorrectly it has to be multiplied into every GL modelview matrix. */
3881 if (context->swapchain->device->view_ident)
3883 gl_info->gl_ops.gl.p_glLoadMatrixf(&state->transforms[WINED3D_TS_WORLD_MATRIX(matrix)].u.m[0][0]);
3884 checkGLcall("glLoadMatrixf");
3888 gl_info->gl_ops.gl.p_glLoadMatrixf(&state->transforms[WINED3D_TS_VIEW].u.m[0][0]);
3889 checkGLcall("glLoadMatrixf");
3890 gl_info->gl_ops.gl.p_glMultMatrixf(&state->transforms[WINED3D_TS_WORLD_MATRIX(matrix)].u.m[0][0]);
3891 checkGLcall("glMultMatrixf");
3895 static void state_vertexblend_w(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3897 enum wined3d_vertex_blend_flags f = state->render_states[WINED3D_RS_VERTEXBLEND];
3898 static unsigned int once;
3900 if (f == WINED3D_VBF_DISABLE)
3903 if (!once++) FIXME("Vertex blend flags %#x not supported.\n", f);
3904 else WARN("Vertex blend flags %#x not supported.\n", f);
3907 static void state_vertexblend(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3909 enum wined3d_vertex_blend_flags val = state->render_states[WINED3D_RS_VERTEXBLEND];
3910 struct wined3d_device *device = context->swapchain->device;
3911 const struct wined3d_gl_info *gl_info = context->gl_info;
3912 static unsigned int once;
3916 case WINED3D_VBF_1WEIGHTS:
3917 case WINED3D_VBF_2WEIGHTS:
3918 case WINED3D_VBF_3WEIGHTS:
3919 gl_info->gl_ops.gl.p_glEnable(GL_VERTEX_BLEND_ARB);
3920 checkGLcall("glEnable(GL_VERTEX_BLEND_ARB)");
3922 /* D3D adds one more matrix which has weight (1 - sum(weights)).
3923 * This is enabled at context creation with enabling
3924 * GL_WEIGHT_SUM_UNITY_ARB. */
3925 GL_EXTCALL(glVertexBlendARB(state->render_states[WINED3D_RS_VERTEXBLEND] + 1));
3927 if (!device->vertexBlendUsed)
3930 for (i = 1; i < gl_info->limits.blends; ++i)
3932 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(i))))
3933 transform_worldex(context, state, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(i)));
3935 device->vertexBlendUsed = TRUE;
3939 case WINED3D_VBF_TWEENING:
3940 case WINED3D_VBF_0WEIGHTS: /* Indexed vertex blending, not supported. */
3941 if (!once++) FIXME("Vertex blend flags %#x not supported.\n", val);
3942 else WARN("Vertex blend flags %#x not supported.\n", val);
3944 case WINED3D_VBF_DISABLE:
3945 gl_info->gl_ops.gl.p_glDisable(GL_VERTEX_BLEND_ARB);
3946 checkGLcall("glDisable(GL_VERTEX_BLEND_ARB)");
3951 static void transform_view(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
3953 const struct wined3d_gl_info *gl_info = context->gl_info;
3954 const struct wined3d_light_info *light = NULL;
3957 /* If we are changing the View matrix, reset the light and clipping planes to the new view
3958 * NOTE: We have to reset the positions even if the light/plane is not currently
3959 * enabled, since the call to enable it will not reset the position.
3960 * NOTE2: Apparently texture transforms do NOT need reapplying
3963 gl_info->gl_ops.gl.p_glMatrixMode(GL_MODELVIEW);
3964 checkGLcall("glMatrixMode(GL_MODELVIEW)");
3965 gl_info->gl_ops.gl.p_glLoadMatrixf(&state->transforms[WINED3D_TS_VIEW].u.m[0][0]);
3966 checkGLcall("glLoadMatrixf(...)");
3968 /* Reset lights. TODO: Call light apply func */
3969 for (k = 0; k < gl_info->limits.lights; ++k)
3971 if (!(light = state->lights[k]))
3973 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + light->glIndex, GL_POSITION, light->lightPosn);
3974 checkGLcall("glLightfv posn");
3975 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + light->glIndex, GL_SPOT_DIRECTION, light->lightDirn);
3976 checkGLcall("glLightfv dirn");
3979 /* Reset Clipping Planes */
3980 for (k = 0; k < gl_info->limits.clipplanes; ++k)
3982 if (!isStateDirty(context, STATE_CLIPPLANE(k)))
3983 clipplane(context, state, STATE_CLIPPLANE(k));
3986 if (context->last_was_rhw)
3988 gl_info->gl_ops.gl.p_glLoadIdentity();
3989 checkGLcall("glLoadIdentity()");
3990 /* No need to update the world matrix, the identity is fine */
3994 /* Call the world matrix state, this will apply the combined WORLD + VIEW matrix
3995 * No need to do it here if the state is scheduled for update. */
3996 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(0))))
3997 transform_world(context, state, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(0)));
3999 /* Avoid looping over a number of matrices if the app never used the functionality */
4000 if (context->swapchain->device->vertexBlendUsed)
4002 for (k = 1; k < gl_info->limits.blends; ++k)
4004 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(k))))
4005 transform_worldex(context, state, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(k)));
4010 static void transform_projection(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4012 const struct wined3d_gl_info *gl_info = context->gl_info;
4014 gl_info->gl_ops.gl.p_glMatrixMode(GL_PROJECTION);
4015 checkGLcall("glMatrixMode(GL_PROJECTION)");
4017 /* There are a couple of additional things we have to take into account
4018 * here besides the projection transformation itself:
4019 * - We need to flip along the y-axis in case of offscreen rendering.
4020 * - OpenGL Z range is {-Wc,...,Wc} while D3D Z range is {0,...,Wc}.
4021 * - D3D coordinates refer to pixel centers while GL coordinates refer
4023 * - D3D has a top-left filling convention. We need to maintain this
4024 * even after the y-flip mentioned above.
4025 * In order to handle the last two points, we translate by
4026 * (63.0 / 128.0) / VPw and (63.0 / 128.0) / VPh. This is equivalent to
4027 * translating slightly less than half a pixel. We want the difference to
4028 * be large enough that it doesn't get lost due to rounding inside the
4029 * driver, but small enough to prevent it from interfering with any
4032 if (context->last_was_rhw)
4034 /* Transform D3D RHW coordinates to OpenGL clip coordinates. */
4035 double x = state->viewport.x;
4036 double y = state->viewport.y;
4037 double w = state->viewport.width;
4038 double h = state->viewport.height;
4039 double x_scale = 2.0 / w;
4040 double x_offset = ((63.0 / 64.0) - (2.0 * x) - w) / w;
4041 double y_scale = context->render_offscreen ? 2.0 / h : 2.0 / -h;
4042 double y_offset = context->render_offscreen
4043 ? ((63.0 / 64.0) - (2.0 * y) - h) / h
4044 : ((63.0 / 64.0) - (2.0 * y) - h) / -h;
4045 const GLdouble projection[] =
4047 x_scale, 0.0, 0.0, 0.0,
4048 0.0, y_scale, 0.0, 0.0,
4050 x_offset, y_offset, -1.0, 1.0,
4053 gl_info->gl_ops.gl.p_glLoadMatrixd(projection);
4054 checkGLcall("glLoadMatrixd");
4058 double y_scale = context->render_offscreen ? -1.0 : 1.0;
4059 double x_offset = (63.0 / 64.0) / state->viewport.width;
4060 double y_offset = context->render_offscreen
4061 ? (63.0 / 64.0) / state->viewport.height
4062 : -(63.0 / 64.0) / state->viewport.height;
4063 const GLdouble projection[] =
4066 0.0, y_scale, 0.0, 0.0,
4068 x_offset, y_offset, -1.0, 1.0,
4071 gl_info->gl_ops.gl.p_glLoadMatrixd(projection);
4072 checkGLcall("glLoadMatrixd");
4074 gl_info->gl_ops.gl.p_glMultMatrixf(&state->transforms[WINED3D_TS_PROJECTION].u.m[0][0]);
4075 checkGLcall("glLoadMatrixf");
4079 /* This should match any arrays loaded in load_vertex_data.
4080 * TODO: Only load / unload arrays if we have to. */
4081 static void unload_vertex_data(const struct wined3d_gl_info *gl_info)
4083 gl_info->gl_ops.gl.p_glDisableClientState(GL_VERTEX_ARRAY);
4084 gl_info->gl_ops.gl.p_glDisableClientState(GL_NORMAL_ARRAY);
4085 gl_info->gl_ops.gl.p_glDisableClientState(GL_COLOR_ARRAY);
4086 if (gl_info->supported[EXT_SECONDARY_COLOR])
4087 gl_info->gl_ops.gl.p_glDisableClientState(GL_SECONDARY_COLOR_ARRAY_EXT);
4088 if (gl_info->supported[ARB_VERTEX_BLEND])
4089 gl_info->gl_ops.gl.p_glDisableClientState(GL_WEIGHT_ARRAY_ARB);
4090 unload_tex_coords(gl_info);
4093 static inline void unload_numbered_array(struct wined3d_context *context, int i)
4095 const struct wined3d_gl_info *gl_info = context->gl_info;
4097 GL_EXTCALL(glDisableVertexAttribArrayARB(i));
4098 checkGLcall("glDisableVertexAttribArrayARB(reg)");
4100 context->numbered_array_mask &= ~(1 << i);
4103 /* This should match any arrays loaded in loadNumberedArrays
4104 * TODO: Only load / unload arrays if we have to. */
4105 static void unload_numbered_arrays(struct wined3d_context *context)
4107 /* disable any attribs (this is the same for both GLSL and ARB modes) */
4110 for (i = 0; i < context->gl_info->limits.vertex_attribs; ++i) {
4111 unload_numbered_array(context, i);
4115 static void load_numbered_arrays(struct wined3d_context *context,
4116 const struct wined3d_stream_info *stream_info, const struct wined3d_state *state)
4118 struct wined3d_device *device = context->swapchain->device;
4119 const struct wined3d_gl_info *gl_info = context->gl_info;
4120 GLuint curVBO = gl_info->supported[ARB_VERTEX_BUFFER_OBJECT] ? ~0U : 0;
4123 /* Default to no instancing */
4124 device->instancedDraw = FALSE;
4126 for (i = 0; i < MAX_ATTRIBS; i++)
4128 const struct wined3d_stream_state *stream;
4130 if (!(stream_info->use_map & (1 << i)))
4132 if (context->numbered_array_mask & (1 << i))
4133 unload_numbered_array(context, i);
4134 if (state->vertex_shader->reg_maps.input_registers & (1 << i))
4135 GL_EXTCALL(glVertexAttrib4fARB(i, 0.0f, 0.0f, 0.0f, 0.0f));
4139 stream = &state->streams[stream_info->elements[i].stream_idx];
4141 /* Do not load instance data. It will be specified using glTexCoord by drawprim */
4142 if (stream->flags & WINED3DSTREAMSOURCE_INSTANCEDATA)
4144 if (context->numbered_array_mask & (1 << i)) unload_numbered_array(context, i);
4145 device->instancedDraw = TRUE;
4149 TRACE_(d3d_shader)("Loading array %u [VBO=%u]\n", i, stream_info->elements[i].data.buffer_object);
4151 if (stream_info->elements[i].stride)
4153 if (curVBO != stream_info->elements[i].data.buffer_object)
4155 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, stream_info->elements[i].data.buffer_object));
4156 checkGLcall("glBindBufferARB");
4157 curVBO = stream_info->elements[i].data.buffer_object;
4159 /* Use the VBO to find out if a vertex buffer exists, not the vb
4160 * pointer. vb can point to a user pointer data blob. In that case
4161 * curVBO will be 0. If there is a vertex buffer but no vbo we
4162 * won't be load converted attributes anyway. */
4163 GL_EXTCALL(glVertexAttribPointerARB(i, stream_info->elements[i].format->gl_vtx_format,
4164 stream_info->elements[i].format->gl_vtx_type,
4165 stream_info->elements[i].format->gl_normalized,
4166 stream_info->elements[i].stride, stream_info->elements[i].data.addr
4167 + state->load_base_vertex_index * stream_info->elements[i].stride));
4169 if (!(context->numbered_array_mask & (1 << i)))
4171 GL_EXTCALL(glEnableVertexAttribArrayARB(i));
4172 context->numbered_array_mask |= (1 << i);
4177 /* Stride = 0 means always the same values.
4178 * glVertexAttribPointerARB doesn't do that. Instead disable the
4179 * pointer and set up the attribute statically. But we have to
4180 * figure out the system memory address. */
4181 const BYTE *ptr = stream_info->elements[i].data.addr;
4182 if (stream_info->elements[i].data.buffer_object)
4184 ptr += (ULONG_PTR)buffer_get_sysmem(stream->buffer, gl_info);
4187 if (context->numbered_array_mask & (1 << i)) unload_numbered_array(context, i);
4189 switch (stream_info->elements[i].format->id)
4191 case WINED3DFMT_R32_FLOAT:
4192 GL_EXTCALL(glVertexAttrib1fvARB(i, (const GLfloat *)ptr));
4194 case WINED3DFMT_R32G32_FLOAT:
4195 GL_EXTCALL(glVertexAttrib2fvARB(i, (const GLfloat *)ptr));
4197 case WINED3DFMT_R32G32B32_FLOAT:
4198 GL_EXTCALL(glVertexAttrib3fvARB(i, (const GLfloat *)ptr));
4200 case WINED3DFMT_R32G32B32A32_FLOAT:
4201 GL_EXTCALL(glVertexAttrib4fvARB(i, (const GLfloat *)ptr));
4204 case WINED3DFMT_R8G8B8A8_UINT:
4205 GL_EXTCALL(glVertexAttrib4NubvARB(i, ptr));
4207 case WINED3DFMT_B8G8R8A8_UNORM:
4208 if (gl_info->supported[ARB_VERTEX_ARRAY_BGRA])
4210 const DWORD *src = (const DWORD *)ptr;
4211 DWORD c = *src & 0xff00ff00;
4212 c |= (*src & 0xff0000) >> 16;
4213 c |= (*src & 0xff) << 16;
4214 GL_EXTCALL(glVertexAttrib4NubvARB(i, (GLubyte *)&c));
4217 /* else fallthrough */
4218 case WINED3DFMT_R8G8B8A8_UNORM:
4219 GL_EXTCALL(glVertexAttrib4NubvARB(i, ptr));
4222 case WINED3DFMT_R16G16_SINT:
4223 GL_EXTCALL(glVertexAttrib4svARB(i, (const GLshort *)ptr));
4225 case WINED3DFMT_R16G16B16A16_SINT:
4226 GL_EXTCALL(glVertexAttrib4svARB(i, (const GLshort *)ptr));
4229 case WINED3DFMT_R16G16_SNORM:
4231 const GLshort s[4] = {((const GLshort *)ptr)[0], ((const GLshort *)ptr)[1], 0, 1};
4232 GL_EXTCALL(glVertexAttrib4NsvARB(i, s));
4235 case WINED3DFMT_R16G16_UNORM:
4237 const GLushort s[4] = {((const GLushort *)ptr)[0], ((const GLushort *)ptr)[1], 0, 1};
4238 GL_EXTCALL(glVertexAttrib4NusvARB(i, s));
4241 case WINED3DFMT_R16G16B16A16_SNORM:
4242 GL_EXTCALL(glVertexAttrib4NsvARB(i, (const GLshort *)ptr));
4244 case WINED3DFMT_R16G16B16A16_UNORM:
4245 GL_EXTCALL(glVertexAttrib4NusvARB(i, (const GLushort *)ptr));
4248 case WINED3DFMT_R10G10B10A2_UINT:
4249 FIXME("Unsure about WINED3DDECLTYPE_UDEC3\n");
4250 /*glVertexAttrib3usvARB(i, (const GLushort *)ptr); Does not exist */
4252 case WINED3DFMT_R10G10B10A2_SNORM:
4253 FIXME("Unsure about WINED3DDECLTYPE_DEC3N\n");
4254 /*glVertexAttrib3NusvARB(i, (const GLushort *)ptr); Does not exist */
4257 case WINED3DFMT_R16G16_FLOAT:
4258 /* Are those 16 bit floats. C doesn't have a 16 bit float type. I could read the single bits and calculate a 4
4259 * byte float according to the IEEE standard
4261 FIXME("Unsupported WINED3DDECLTYPE_FLOAT16_2\n");
4263 case WINED3DFMT_R16G16B16A16_FLOAT:
4264 FIXME("Unsupported WINED3DDECLTYPE_FLOAT16_4\n");
4268 ERR("Unexpected declaration in stride 0 attributes\n");
4274 checkGLcall("Loading numbered arrays");
4277 static void load_vertex_data(const struct wined3d_context *context,
4278 const struct wined3d_stream_info *si, const struct wined3d_state *state)
4280 struct wined3d_device *device = context->swapchain->device;
4281 const struct wined3d_gl_info *gl_info = context->gl_info;
4282 GLuint curVBO = gl_info->supported[ARB_VERTEX_BUFFER_OBJECT] ? ~0U : 0;
4283 const struct wined3d_stream_info_element *e;
4285 TRACE("Using fast vertex array code\n");
4287 /* This is fixed function pipeline only, and the fixed function pipeline doesn't do instancing */
4288 device->instancedDraw = FALSE;
4290 /* Blend Data ---------------------------------------------- */
4291 if ((si->use_map & (1 << WINED3D_FFP_BLENDWEIGHT))
4292 || si->use_map & (1 << WINED3D_FFP_BLENDINDICES))
4294 e = &si->elements[WINED3D_FFP_BLENDWEIGHT];
4296 if (gl_info->supported[ARB_VERTEX_BLEND])
4298 TRACE("Blend %u %p %u\n", e->format->component_count,
4299 e->data.addr + state->load_base_vertex_index * e->stride, e->stride);
4301 gl_info->gl_ops.gl.p_glEnableClientState(GL_WEIGHT_ARRAY_ARB);
4302 checkGLcall("glEnableClientState(GL_WEIGHT_ARRAY_ARB)");
4304 GL_EXTCALL(glVertexBlendARB(e->format->component_count + 1));
4306 if (curVBO != e->data.buffer_object)
4308 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->data.buffer_object));
4309 checkGLcall("glBindBufferARB");
4310 curVBO = e->data.buffer_object;
4313 TRACE("glWeightPointerARB(%#x, %#x, %#x, %p);\n",
4314 e->format->gl_vtx_format,
4315 e->format->gl_vtx_type,
4317 e->data.addr + state->load_base_vertex_index * e->stride);
4318 GL_EXTCALL(glWeightPointerARB(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
4319 e->data.addr + state->load_base_vertex_index * e->stride));
4321 checkGLcall("glWeightPointerARB");
4323 if (si->use_map & (1 << WINED3D_FFP_BLENDINDICES))
4328 FIXME("blendMatrixIndices support\n");
4333 /* TODO: support blends in drawStridedSlow
4334 * No need to write a FIXME here, this is done after the general vertex decl decoding
4336 WARN("unsupported blending in openGl\n");
4341 if (gl_info->supported[ARB_VERTEX_BLEND])
4343 static const GLbyte one = 1;
4344 GL_EXTCALL(glWeightbvARB(1, &one));
4345 checkGLcall("glWeightbvARB(gl_info->max_blends, weights)");
4349 /* Point Size ----------------------------------------------*/
4350 if (si->use_map & (1 << WINED3D_FFP_PSIZE))
4352 /* no such functionality in the fixed function GL pipeline */
4353 TRACE("Cannot change ptSize here in openGl\n");
4354 /* TODO: Implement this function in using shaders if they are available */
4357 /* Vertex Pointers -----------------------------------------*/
4358 if (si->use_map & (1 << WINED3D_FFP_POSITION))
4360 e = &si->elements[WINED3D_FFP_POSITION];
4362 if (curVBO != e->data.buffer_object)
4364 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->data.buffer_object));
4365 checkGLcall("glBindBufferARB");
4366 curVBO = e->data.buffer_object;
4369 TRACE("glVertexPointer(%#x, %#x, %#x, %p);\n",
4370 e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
4371 e->data.addr + state->load_base_vertex_index * e->stride);
4372 gl_info->gl_ops.gl.p_glVertexPointer(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
4373 e->data.addr + state->load_base_vertex_index * e->stride);
4374 checkGLcall("glVertexPointer(...)");
4375 gl_info->gl_ops.gl.p_glEnableClientState(GL_VERTEX_ARRAY);
4376 checkGLcall("glEnableClientState(GL_VERTEX_ARRAY)");
4379 /* Normals -------------------------------------------------*/
4380 if (si->use_map & (1 << WINED3D_FFP_NORMAL))
4382 e = &si->elements[WINED3D_FFP_NORMAL];
4384 if (curVBO != e->data.buffer_object)
4386 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->data.buffer_object));
4387 checkGLcall("glBindBufferARB");
4388 curVBO = e->data.buffer_object;
4391 TRACE("glNormalPointer(%#x, %#x, %p);\n", e->format->gl_vtx_type, e->stride,
4392 e->data.addr + state->load_base_vertex_index * e->stride);
4393 gl_info->gl_ops.gl.p_glNormalPointer(e->format->gl_vtx_type, e->stride,
4394 e->data.addr + state->load_base_vertex_index * e->stride);
4395 checkGLcall("glNormalPointer(...)");
4396 gl_info->gl_ops.gl.p_glEnableClientState(GL_NORMAL_ARRAY);
4397 checkGLcall("glEnableClientState(GL_NORMAL_ARRAY)");
4402 gl_info->gl_ops.gl.p_glNormal3f(0, 0, 0);
4403 checkGLcall("glNormal3f(0, 0, 0)");
4406 /* Diffuse Colour --------------------------------------------*/
4407 if (si->use_map & (1 << WINED3D_FFP_DIFFUSE))
4409 e = &si->elements[WINED3D_FFP_DIFFUSE];
4411 if (curVBO != e->data.buffer_object)
4413 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->data.buffer_object));
4414 checkGLcall("glBindBufferARB");
4415 curVBO = e->data.buffer_object;
4418 TRACE("glColorPointer(%#x, %#x %#x, %p);\n",
4419 e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
4420 e->data.addr + state->load_base_vertex_index * e->stride);
4421 gl_info->gl_ops.gl.p_glColorPointer(e->format->gl_vtx_format, e->format->gl_vtx_type, e->stride,
4422 e->data.addr + state->load_base_vertex_index * e->stride);
4423 checkGLcall("glColorPointer(4, GL_UNSIGNED_BYTE, ...)");
4424 gl_info->gl_ops.gl.p_glEnableClientState(GL_COLOR_ARRAY);
4425 checkGLcall("glEnableClientState(GL_COLOR_ARRAY)");
4430 gl_info->gl_ops.gl.p_glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
4431 checkGLcall("glColor4f(1, 1, 1, 1)");
4434 /* Specular Colour ------------------------------------------*/
4435 if (si->use_map & (1 << WINED3D_FFP_SPECULAR))
4437 TRACE("setting specular colour\n");
4439 e = &si->elements[WINED3D_FFP_SPECULAR];
4441 if (gl_info->supported[EXT_SECONDARY_COLOR])
4443 GLenum type = e->format->gl_vtx_type;
4444 GLint format = e->format->gl_vtx_format;
4446 if (curVBO != e->data.buffer_object)
4448 GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, e->data.buffer_object));
4449 checkGLcall("glBindBufferARB");
4450 curVBO = e->data.buffer_object;
4453 if (format != 4 || (gl_info->quirks & WINED3D_QUIRK_ALLOWS_SPECULAR_ALPHA))
4455 /* Usually specular colors only allow 3 components, since they have no alpha. In D3D, the specular alpha
4456 * contains the fog coordinate, which is passed to GL with GL_EXT_fog_coord. However, the fixed function
4457 * vertex pipeline can pass the specular alpha through, and pixel shaders can read it. So it GL accepts
4458 * 4 component secondary colors use it
4460 TRACE("glSecondaryColorPointer(%#x, %#x, %#x, %p);\n", format, type, e->stride,
4461 e->data.addr + state->load_base_vertex_index * e->stride);
4462 GL_EXTCALL(glSecondaryColorPointerEXT(format, type, e->stride,
4463 e->data.addr + state->load_base_vertex_index * e->stride));
4464 checkGLcall("glSecondaryColorPointerEXT(format, type, ...)");
4470 case GL_UNSIGNED_BYTE:
4471 TRACE("glSecondaryColorPointer(3, GL_UNSIGNED_BYTE, %#x, %p);\n", e->stride,
4472 e->data.addr + state->load_base_vertex_index * e->stride);
4473 GL_EXTCALL(glSecondaryColorPointerEXT(3, GL_UNSIGNED_BYTE, e->stride,
4474 e->data.addr + state->load_base_vertex_index * e->stride));
4475 checkGLcall("glSecondaryColorPointerEXT(3, GL_UNSIGNED_BYTE, ...)");
4479 FIXME("Add 4 component specular color pointers for type %x\n", type);
4480 /* Make sure that the right color component is dropped */
4481 TRACE("glSecondaryColorPointer(3, %#x, %#x, %p);\n", type, e->stride,
4482 e->data.addr + state->load_base_vertex_index * e->stride);
4483 GL_EXTCALL(glSecondaryColorPointerEXT(3, type, e->stride,
4484 e->data.addr + state->load_base_vertex_index * e->stride));
4485 checkGLcall("glSecondaryColorPointerEXT(3, type, ...)");
4488 gl_info->gl_ops.gl.p_glEnableClientState(GL_SECONDARY_COLOR_ARRAY_EXT);
4489 checkGLcall("glEnableClientState(GL_SECONDARY_COLOR_ARRAY_EXT)");
4493 WARN("Specular colour is not supported in this GL implementation.\n");
4498 if (gl_info->supported[EXT_SECONDARY_COLOR])
4500 GL_EXTCALL(glSecondaryColor3fEXT)(0, 0, 0);
4501 checkGLcall("glSecondaryColor3fEXT(0, 0, 0)");
4505 WARN("Specular colour is not supported in this GL implementation.\n");
4509 /* Texture coords -------------------------------------------*/
4510 load_tex_coords(context, si, &curVBO, state);
4513 static void streamsrc(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4515 const struct wined3d_device *device = context->swapchain->device;
4516 BOOL load_numbered = use_vs(state) && !device->useDrawStridedSlow;
4517 BOOL load_named = !use_vs(state) && !device->useDrawStridedSlow;
4519 if (isStateDirty(context, STATE_VDECL)) return;
4520 if (context->numberedArraysLoaded && !load_numbered)
4522 unload_numbered_arrays(context);
4523 context->numberedArraysLoaded = FALSE;
4524 context->numbered_array_mask = 0;
4526 else if (context->namedArraysLoaded)
4528 unload_vertex_data(context->gl_info);
4529 context->namedArraysLoaded = FALSE;
4534 TRACE("Loading numbered arrays\n");
4535 load_numbered_arrays(context, &device->strided_streams, state);
4536 context->numberedArraysLoaded = TRUE;
4538 else if (load_named)
4540 TRACE("Loading vertex data\n");
4541 load_vertex_data(context, &device->strided_streams, state);
4542 context->namedArraysLoaded = TRUE;
4546 static void vdecl_miscpart(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4548 if (isStateDirty(context, STATE_STREAMSRC))
4550 streamsrc(context, state, STATE_STREAMSRC);
4553 static void vertexdeclaration(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4555 const struct wined3d_device *device = context->swapchain->device;
4556 const struct wined3d_gl_info *gl_info = context->gl_info;
4557 BOOL useVertexShaderFunction = use_vs(state);
4558 BOOL updateFog = FALSE;
4560 BOOL wasrhw = context->last_was_rhw;
4563 transformed = device->strided_streams.position_transformed;
4564 if (transformed != context->last_was_rhw && !useVertexShaderFunction)
4567 context->last_was_rhw = transformed;
4569 /* Don't have to apply the matrices when vertex shaders are used. When
4570 * vshaders are turned off this function will be called again anyway to
4571 * make sure they're properly set. */
4572 if (!useVertexShaderFunction)
4574 /* TODO: Move this mainly to the viewport state and only apply when
4575 * the vp has changed or transformed / untransformed was switched. */
4576 if (wasrhw != context->last_was_rhw
4577 && !isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_PROJECTION))
4578 && !isStateDirty(context, STATE_VIEWPORT))
4579 transform_projection(context, state, STATE_TRANSFORM(WINED3D_TS_PROJECTION));
4580 /* World matrix needs reapplication here only if we're switching between rhw and non-rhw
4583 * If a vertex shader is used, the world matrix changed and then vertex shader unbound
4584 * this check will fail and the matrix not applied again. This is OK because a simple
4585 * world matrix change reapplies the matrix - These checks here are only to satisfy the
4586 * needs of the vertex declaration.
4588 * World and view matrix go into the same gl matrix, so only apply them when neither is
4591 if (transformed != wasrhw && !isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(0)))
4592 && !isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_VIEW)))
4593 transform_world(context, state, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(0)));
4594 if (!isStateDirty(context, STATE_RENDER(WINED3D_RS_COLORVERTEX)))
4595 state_colormat(context, state, STATE_RENDER(WINED3D_RS_COLORVERTEX));
4596 if (!isStateDirty(context, STATE_RENDER(WINED3D_RS_LIGHTING)))
4597 state_lighting(context, state, STATE_RENDER(WINED3D_RS_LIGHTING));
4599 if (context->last_was_vshader)
4603 if (!device->vs_clipping && !isStateDirty(context, STATE_RENDER(WINED3D_RS_CLIPPLANEENABLE)))
4604 state_clipping(context, state, STATE_RENDER(WINED3D_RS_CLIPPLANEENABLE));
4606 for (i = 0; i < gl_info->limits.clipplanes; ++i)
4608 clipplane(context, state, STATE_CLIPPLANE(i));
4611 if (!isStateDirty(context, STATE_RENDER(WINED3D_RS_NORMALIZENORMALS)))
4612 state_normalize(context, state, STATE_RENDER(WINED3D_RS_NORMALIZENORMALS));
4616 if(!context->last_was_vshader) {
4617 static BOOL warned = FALSE;
4618 if(!device->vs_clipping) {
4619 /* Disable all clip planes to get defined results on all drivers. See comment in the
4620 * state_clipping state handler
4622 for (i = 0; i < gl_info->limits.clipplanes; ++i)
4624 gl_info->gl_ops.gl.p_glDisable(GL_CLIP_PLANE0 + i);
4625 checkGLcall("glDisable(GL_CLIP_PLANE0 + i)");
4628 if (!warned && state->render_states[WINED3D_RS_CLIPPLANEENABLE])
4630 FIXME("Clipping not supported with vertex shaders\n");
4636 /* Apply the transform matrices when switching from rhw
4637 * drawing to vertex shaders. Vertex shaders themselves do
4638 * not need it, but the matrices are not reapplied
4639 * automatically when switching back from vertex shaders to
4640 * fixed function processing. So make sure we leave the fixed
4641 * function vertex processing states back in a sane state
4642 * before switching to shaders. */
4643 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_PROJECTION)))
4644 transform_projection(context, state, STATE_TRANSFORM(WINED3D_TS_PROJECTION));
4645 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(0))))
4646 transform_world(context, state, STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(0)));
4650 /* Vertex shader clipping ignores the view matrix. Update all clipplanes
4651 * (Note: ARB shaders can read the clip planes for clipping emulation even if
4652 * device->vs_clipping is false.
4654 for (i = 0; i < gl_info->limits.clipplanes; ++i)
4656 clipplane(context, state, STATE_CLIPPLANE(i));
4661 context->last_was_vshader = useVertexShaderFunction;
4662 context->select_shader = 1;
4663 context->load_constants = 1;
4666 context_apply_state(context, state, STATE_RENDER(WINED3D_RS_FOGVERTEXMODE));
4668 if (!useVertexShaderFunction)
4672 for (i = 0; i < MAX_TEXTURES; ++i)
4674 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_TEXTURE0 + i)))
4675 transform_texture(context, state, STATE_TEXTURESTAGE(i, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS));
4679 if (transformed != wasrhw && !isStateDirty(context, STATE_RENDER(WINED3D_RS_ZENABLE)))
4680 state_zenable(context, state, STATE_RENDER(WINED3D_RS_ZENABLE));
4683 static void viewport_miscpart(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4685 const struct wined3d_surface *target = state->fb->render_targets[0];
4686 const struct wined3d_gl_info *gl_info = context->gl_info;
4687 struct wined3d_viewport vp = state->viewport;
4689 if (vp.width > target->resource.width)
4690 vp.width = target->resource.width;
4691 if (vp.height > target->resource.height)
4692 vp.height = target->resource.height;
4694 gl_info->gl_ops.gl.p_glDepthRange(vp.min_z, vp.max_z);
4695 checkGLcall("glDepthRange");
4696 /* Note: GL requires lower left, DirectX supplies upper left. This is
4697 * reversed when using offscreen rendering. */
4698 if (context->render_offscreen)
4700 gl_info->gl_ops.gl.p_glViewport(vp.x, vp.y, vp.width, vp.height);
4706 target->get_drawable_size(context, &width, &height);
4707 gl_info->gl_ops.gl.p_glViewport(vp.x, (height - (vp.y + vp.height)),
4708 vp.width, vp.height);
4711 checkGLcall("glViewport");
4714 static void viewport_vertexpart(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4716 if (!isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_PROJECTION)))
4717 transform_projection(context, state, STATE_TRANSFORM(WINED3D_TS_PROJECTION));
4718 if (!isStateDirty(context, STATE_RENDER(WINED3D_RS_POINTSCALEENABLE)))
4719 state_pscale(context, state, STATE_RENDER(WINED3D_RS_POINTSCALEENABLE));
4720 /* Update the position fixup. */
4721 context->load_constants = 1;
4724 static void light(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4726 const struct wined3d_gl_info *gl_info = context->gl_info;
4727 UINT Index = state_id - STATE_ACTIVELIGHT(0);
4728 const struct wined3d_light_info *lightInfo = state->lights[Index];
4732 gl_info->gl_ops.gl.p_glDisable(GL_LIGHT0 + Index);
4733 checkGLcall("glDisable(GL_LIGHT0 + Index)");
4738 float colRGBA[] = {0.0f, 0.0f, 0.0f, 0.0f};
4740 /* Light settings are affected by the model view in OpenGL, the View transform in direct3d*/
4741 gl_info->gl_ops.gl.p_glMatrixMode(GL_MODELVIEW);
4742 gl_info->gl_ops.gl.p_glPushMatrix();
4743 gl_info->gl_ops.gl.p_glLoadMatrixf(&state->transforms[WINED3D_TS_VIEW].u.m[0][0]);
4746 colRGBA[0] = lightInfo->OriginalParms.diffuse.r;
4747 colRGBA[1] = lightInfo->OriginalParms.diffuse.g;
4748 colRGBA[2] = lightInfo->OriginalParms.diffuse.b;
4749 colRGBA[3] = lightInfo->OriginalParms.diffuse.a;
4750 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + Index, GL_DIFFUSE, colRGBA);
4751 checkGLcall("glLightfv");
4754 colRGBA[0] = lightInfo->OriginalParms.specular.r;
4755 colRGBA[1] = lightInfo->OriginalParms.specular.g;
4756 colRGBA[2] = lightInfo->OriginalParms.specular.b;
4757 colRGBA[3] = lightInfo->OriginalParms.specular.a;
4758 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + Index, GL_SPECULAR, colRGBA);
4759 checkGLcall("glLightfv");
4762 colRGBA[0] = lightInfo->OriginalParms.ambient.r;
4763 colRGBA[1] = lightInfo->OriginalParms.ambient.g;
4764 colRGBA[2] = lightInfo->OriginalParms.ambient.b;
4765 colRGBA[3] = lightInfo->OriginalParms.ambient.a;
4766 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + Index, GL_AMBIENT, colRGBA);
4767 checkGLcall("glLightfv");
4769 if ((lightInfo->OriginalParms.range * lightInfo->OriginalParms.range) >= FLT_MIN)
4770 quad_att = 1.4f / (lightInfo->OriginalParms.range * lightInfo->OriginalParms.range);
4772 quad_att = 0.0f; /* 0 or MAX? (0 seems to be ok) */
4774 /* Do not assign attenuation values for lights that do not use them. D3D apps are free to pass any junk,
4775 * but gl drivers use them and may crash due to bad Attenuation values. Need for Speed most wanted sets
4776 * Attenuation0 to NaN and crashes in the gl lib
4779 switch (lightInfo->OriginalParms.type)
4781 case WINED3D_LIGHT_POINT:
4783 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + Index, GL_POSITION, &lightInfo->lightPosn[0]);
4784 checkGLcall("glLightfv");
4785 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_SPOT_CUTOFF, lightInfo->cutoff);
4786 checkGLcall("glLightf");
4787 /* Attenuation - Are these right? guessing... */
4788 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_CONSTANT_ATTENUATION,
4789 lightInfo->OriginalParms.attenuation0);
4790 checkGLcall("glLightf");
4791 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_LINEAR_ATTENUATION,
4792 lightInfo->OriginalParms.attenuation1);
4793 checkGLcall("glLightf");
4794 if (quad_att < lightInfo->OriginalParms.attenuation2)
4795 quad_att = lightInfo->OriginalParms.attenuation2;
4796 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_QUADRATIC_ATTENUATION, quad_att);
4797 checkGLcall("glLightf");
4801 case WINED3D_LIGHT_SPOT:
4803 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + Index, GL_POSITION, &lightInfo->lightPosn[0]);
4804 checkGLcall("glLightfv");
4806 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + Index, GL_SPOT_DIRECTION, &lightInfo->lightDirn[0]);
4807 checkGLcall("glLightfv");
4808 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_SPOT_EXPONENT, lightInfo->exponent);
4809 checkGLcall("glLightf");
4810 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_SPOT_CUTOFF, lightInfo->cutoff);
4811 checkGLcall("glLightf");
4812 /* Attenuation - Are these right? guessing... */
4813 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_CONSTANT_ATTENUATION,
4814 lightInfo->OriginalParms.attenuation0);
4815 checkGLcall("glLightf");
4816 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_LINEAR_ATTENUATION,
4817 lightInfo->OriginalParms.attenuation1);
4818 checkGLcall("glLightf");
4819 if (quad_att < lightInfo->OriginalParms.attenuation2)
4820 quad_att = lightInfo->OriginalParms.attenuation2;
4821 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_QUADRATIC_ATTENUATION, quad_att);
4822 checkGLcall("glLightf");
4826 case WINED3D_LIGHT_DIRECTIONAL:
4828 /* Note GL uses w position of 0 for direction! */
4829 gl_info->gl_ops.gl.p_glLightfv(GL_LIGHT0 + Index, GL_POSITION, &lightInfo->lightPosn[0]);
4830 checkGLcall("glLightfv");
4831 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_SPOT_CUTOFF, lightInfo->cutoff);
4832 checkGLcall("glLightf");
4833 gl_info->gl_ops.gl.p_glLightf(GL_LIGHT0 + Index, GL_SPOT_EXPONENT, 0.0f);
4834 checkGLcall("glLightf");
4838 FIXME("Unrecognized light type %#x.\n", lightInfo->OriginalParms.type);
4841 /* Restore the modelview matrix */
4842 gl_info->gl_ops.gl.p_glPopMatrix();
4844 gl_info->gl_ops.gl.p_glEnable(GL_LIGHT0 + Index);
4845 checkGLcall("glEnable(GL_LIGHT0 + Index)");
4849 static void scissorrect(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4851 const struct wined3d_gl_info *gl_info = context->gl_info;
4852 const RECT *r = &state->scissor_rect;
4854 /* Warning: glScissor uses window coordinates, not viewport coordinates,
4855 * so our viewport correction does not apply. Warning2: Even in windowed
4856 * mode the coords are relative to the window, not the screen. */
4857 TRACE("Setting new scissor rect to %s.\n", wine_dbgstr_rect(r));
4859 if (context->render_offscreen)
4861 gl_info->gl_ops.gl.p_glScissor(r->left, r->top, r->right - r->left, r->bottom - r->top);
4865 const struct wined3d_surface *target = state->fb->render_targets[0];
4869 target->get_drawable_size(context, &width, &height);
4870 gl_info->gl_ops.gl.p_glScissor(r->left, height - r->bottom, r->right - r->left, r->bottom - r->top);
4872 checkGLcall("glScissor");
4875 static void indexbuffer(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4877 const struct wined3d_stream_info *stream_info = &context->swapchain->device->strided_streams;
4878 const struct wined3d_gl_info *gl_info = context->gl_info;
4880 if (state->user_stream || !state->index_buffer || !stream_info->all_vbo)
4882 GL_EXTCALL(glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0));
4886 struct wined3d_buffer *ib = state->index_buffer;
4887 GL_EXTCALL(glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, ib->buffer_object));
4891 static void frontface(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4893 const struct wined3d_gl_info *gl_info = context->gl_info;
4895 if (context->render_offscreen)
4897 gl_info->gl_ops.gl.p_glFrontFace(GL_CCW);
4898 checkGLcall("glFrontFace(GL_CCW)");
4902 gl_info->gl_ops.gl.p_glFrontFace(GL_CW);
4903 checkGLcall("glFrontFace(GL_CW)");
4907 static void psorigin_w(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4913 WARN("Point sprite coordinate origin switching not supported.\n");
4918 static void psorigin(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4920 const struct wined3d_gl_info *gl_info = context->gl_info;
4921 GLint origin = context->render_offscreen ? GL_LOWER_LEFT : GL_UPPER_LEFT;
4923 if (gl_info->supported[NV_POINT_SPRITE])
4925 GL_EXTCALL(glPointParameteriNV(GL_POINT_SPRITE_COORD_ORIGIN, origin));
4926 checkGLcall("glPointParameteriNV(GL_POINT_SPRITE_COORD_ORIGIN, ...)");
4930 void state_srgbwrite(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
4932 const struct wined3d_gl_info *gl_info = context->gl_info;
4933 const struct wined3d_surface *rt = state->fb->render_targets[0];
4935 TRACE("context %p, state %p, state_id %#x.\n", context, state, state_id);
4937 if (state->render_states[WINED3D_RS_SRGBWRITEENABLE]
4938 && rt->resource.format->flags & WINED3DFMT_FLAG_SRGB_WRITE)
4939 gl_info->gl_ops.gl.p_glEnable(GL_FRAMEBUFFER_SRGB);
4941 gl_info->gl_ops.gl.p_glDisable(GL_FRAMEBUFFER_SRGB);
4944 const struct StateEntryTemplate misc_state_template[] = {
4945 { STATE_RENDER(WINED3D_RS_SRCBLEND), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4946 { STATE_RENDER(WINED3D_RS_DESTBLEND), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4947 { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), state_blend }, WINED3D_GL_EXT_NONE },
4948 { STATE_RENDER(WINED3D_RS_EDGEANTIALIAS), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4949 { STATE_RENDER(WINED3D_RS_ANTIALIASEDLINEENABLE), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4950 { STATE_RENDER(WINED3D_RS_SEPARATEALPHABLENDENABLE), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4951 { STATE_RENDER(WINED3D_RS_SRCBLENDALPHA), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4952 { STATE_RENDER(WINED3D_RS_DESTBLENDALPHA), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4953 { STATE_RENDER(WINED3D_RS_DESTBLENDALPHA), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4954 { STATE_RENDER(WINED3D_RS_BLENDOPALPHA), { STATE_RENDER(WINED3D_RS_ALPHABLENDENABLE), NULL }, WINED3D_GL_EXT_NONE },
4955 { STATE_STREAMSRC, { STATE_STREAMSRC, streamsrc }, WINED3D_GL_EXT_NONE },
4956 { STATE_VDECL, { STATE_VDECL, vdecl_miscpart }, WINED3D_GL_EXT_NONE },
4957 { STATE_FRONTFACE, { STATE_FRONTFACE, frontface }, WINED3D_GL_EXT_NONE },
4958 { STATE_SCISSORRECT, { STATE_SCISSORRECT, scissorrect }, WINED3D_GL_EXT_NONE },
4959 { STATE_POINTSPRITECOORDORIGIN, { STATE_POINTSPRITECOORDORIGIN, psorigin }, WINED3D_GL_VERSION_2_0 },
4960 { STATE_POINTSPRITECOORDORIGIN, { STATE_POINTSPRITECOORDORIGIN, psorigin_w }, WINED3D_GL_EXT_NONE },
4962 /* TODO: Move shader constant loading to vertex and fragment pipeline respectively, as soon as the pshader and
4963 * vshader loadings are untied from each other
4965 { STATE_VERTEXSHADERCONSTANT, { STATE_VERTEXSHADERCONSTANT, shaderconstant }, WINED3D_GL_EXT_NONE },
4966 { STATE_PIXELSHADERCONSTANT, { STATE_VERTEXSHADERCONSTANT, NULL }, WINED3D_GL_EXT_NONE },
4967 { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4968 { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4969 { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4970 { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4971 { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4972 { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4973 { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4974 { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4975 { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4976 { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4977 { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4978 { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4979 { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4980 { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4981 { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4982 { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4983 { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4984 { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4985 { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4986 { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4987 { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4988 { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4989 { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4990 { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4991 { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4992 { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4993 { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4994 { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4995 { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT00), { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT00), shader_bumpenvmat }, WINED3D_GL_EXT_NONE },
4996 { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT01), { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4997 { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT10), { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4998 { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT11), { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_MAT00), NULL }, WINED3D_GL_EXT_NONE },
4999 { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5000 { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(0, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5001 { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5002 { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(1, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5003 { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5004 { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(2, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5005 { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5006 { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(3, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5007 { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5008 { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(4, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5009 { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5010 { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(5, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5011 { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5012 { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(6, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5013 { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_LSCALE), { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_LSCALE), tex_bumpenvlscale }, WINED3D_GL_EXT_NONE },
5014 { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_LOFFSET), { STATE_TEXTURESTAGE(7, WINED3D_TSS_BUMPENV_LSCALE), NULL }, WINED3D_GL_EXT_NONE },
5016 { STATE_VIEWPORT, { STATE_VIEWPORT, viewport_miscpart }, WINED3D_GL_EXT_NONE },
5017 { STATE_INDEXBUFFER, { STATE_INDEXBUFFER, indexbuffer }, ARB_VERTEX_BUFFER_OBJECT },
5018 { STATE_INDEXBUFFER, { STATE_INDEXBUFFER, state_nop }, WINED3D_GL_EXT_NONE },
5019 { STATE_RENDER(WINED3D_RS_ANTIALIAS), { STATE_RENDER(WINED3D_RS_ANTIALIAS), state_antialias }, WINED3D_GL_EXT_NONE },
5020 { STATE_RENDER(WINED3D_RS_TEXTUREPERSPECTIVE), { STATE_RENDER(WINED3D_RS_TEXTUREPERSPECTIVE), state_perspective }, WINED3D_GL_EXT_NONE },
5021 { STATE_RENDER(WINED3D_RS_ZENABLE), { STATE_RENDER(WINED3D_RS_ZENABLE), state_zenable }, WINED3D_GL_EXT_NONE },
5022 { STATE_RENDER(WINED3D_RS_WRAPU), { STATE_RENDER(WINED3D_RS_WRAPU), state_wrapu }, WINED3D_GL_EXT_NONE },
5023 { STATE_RENDER(WINED3D_RS_WRAPV), { STATE_RENDER(WINED3D_RS_WRAPV), state_wrapv }, WINED3D_GL_EXT_NONE },
5024 { STATE_RENDER(WINED3D_RS_FILLMODE), { STATE_RENDER(WINED3D_RS_FILLMODE), state_fillmode }, WINED3D_GL_EXT_NONE },
5025 { STATE_RENDER(WINED3D_RS_SHADEMODE), { STATE_RENDER(WINED3D_RS_SHADEMODE), state_shademode }, WINED3D_GL_EXT_NONE },
5026 { STATE_RENDER(WINED3D_RS_LINEPATTERN), { STATE_RENDER(WINED3D_RS_LINEPATTERN), state_linepattern }, WINED3D_GL_EXT_NONE },
5027 { STATE_RENDER(WINED3D_RS_MONOENABLE), { STATE_RENDER(WINED3D_RS_MONOENABLE), state_monoenable }, WINED3D_GL_EXT_NONE },
5028 { STATE_RENDER(WINED3D_RS_ROP2), { STATE_RENDER(WINED3D_RS_ROP2), state_rop2 }, WINED3D_GL_EXT_NONE },
5029 { STATE_RENDER(WINED3D_RS_PLANEMASK), { STATE_RENDER(WINED3D_RS_PLANEMASK), state_planemask }, WINED3D_GL_EXT_NONE },
5030 { STATE_RENDER(WINED3D_RS_ZWRITEENABLE), { STATE_RENDER(WINED3D_RS_ZWRITEENABLE), state_zwritenable }, WINED3D_GL_EXT_NONE },
5031 { STATE_RENDER(WINED3D_RS_ALPHATESTENABLE), { STATE_RENDER(WINED3D_RS_ALPHATESTENABLE), state_alpha }, WINED3D_GL_EXT_NONE },
5032 { STATE_RENDER(WINED3D_RS_ALPHAREF), { STATE_RENDER(WINED3D_RS_ALPHATESTENABLE), NULL }, WINED3D_GL_EXT_NONE },
5033 { STATE_RENDER(WINED3D_RS_ALPHAFUNC), { STATE_RENDER(WINED3D_RS_ALPHATESTENABLE), NULL }, WINED3D_GL_EXT_NONE },
5034 { STATE_RENDER(WINED3D_RS_COLORKEYENABLE), { STATE_RENDER(WINED3D_RS_ALPHATESTENABLE), NULL }, WINED3D_GL_EXT_NONE },
5035 { STATE_RENDER(WINED3D_RS_LASTPIXEL), { STATE_RENDER(WINED3D_RS_LASTPIXEL), state_lastpixel }, WINED3D_GL_EXT_NONE },
5036 { STATE_RENDER(WINED3D_RS_CULLMODE), { STATE_RENDER(WINED3D_RS_CULLMODE), state_cullmode }, WINED3D_GL_EXT_NONE },
5037 { STATE_RENDER(WINED3D_RS_ZFUNC), { STATE_RENDER(WINED3D_RS_ZFUNC), state_zfunc }, WINED3D_GL_EXT_NONE },
5038 { STATE_RENDER(WINED3D_RS_DITHERENABLE), { STATE_RENDER(WINED3D_RS_DITHERENABLE), state_ditherenable }, WINED3D_GL_EXT_NONE },
5039 { STATE_RENDER(WINED3D_RS_SUBPIXEL), { STATE_RENDER(WINED3D_RS_SUBPIXEL), state_subpixel }, WINED3D_GL_EXT_NONE },
5040 { STATE_RENDER(WINED3D_RS_SUBPIXELX), { STATE_RENDER(WINED3D_RS_SUBPIXELX), state_subpixelx }, WINED3D_GL_EXT_NONE },
5041 { STATE_RENDER(WINED3D_RS_STIPPLEDALPHA), { STATE_RENDER(WINED3D_RS_STIPPLEDALPHA), state_stippledalpha }, WINED3D_GL_EXT_NONE },
5042 { STATE_RENDER(WINED3D_RS_STIPPLEENABLE), { STATE_RENDER(WINED3D_RS_STIPPLEENABLE), state_stippleenable }, WINED3D_GL_EXT_NONE },
5043 { STATE_RENDER(WINED3D_RS_MIPMAPLODBIAS), { STATE_RENDER(WINED3D_RS_MIPMAPLODBIAS), state_mipmaplodbias }, WINED3D_GL_EXT_NONE },
5044 { STATE_RENDER(WINED3D_RS_ANISOTROPY), { STATE_RENDER(WINED3D_RS_ANISOTROPY), state_anisotropy }, WINED3D_GL_EXT_NONE },
5045 { STATE_RENDER(WINED3D_RS_FLUSHBATCH), { STATE_RENDER(WINED3D_RS_FLUSHBATCH), state_flushbatch }, WINED3D_GL_EXT_NONE },
5046 { STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT),{ STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT),state_translucentsi }, WINED3D_GL_EXT_NONE },
5047 { STATE_RENDER(WINED3D_RS_STENCILENABLE), { STATE_RENDER(WINED3D_RS_STENCILENABLE), state_stencil }, WINED3D_GL_EXT_NONE },
5048 { STATE_RENDER(WINED3D_RS_STENCILFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5049 { STATE_RENDER(WINED3D_RS_STENCILZFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5050 { STATE_RENDER(WINED3D_RS_STENCILPASS), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5051 { STATE_RENDER(WINED3D_RS_STENCILFUNC), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5052 { STATE_RENDER(WINED3D_RS_STENCILREF), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5053 { STATE_RENDER(WINED3D_RS_STENCILMASK), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5054 { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite2s}, EXT_STENCIL_TWO_SIDE },
5055 { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite }, WINED3D_GL_EXT_NONE },
5056 { STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5057 { STATE_RENDER(WINED3D_RS_CCW_STENCILFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5058 { STATE_RENDER(WINED3D_RS_CCW_STENCILZFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5059 { STATE_RENDER(WINED3D_RS_CCW_STENCILPASS), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5060 { STATE_RENDER(WINED3D_RS_CCW_STENCILFUNC), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE },
5061 { STATE_RENDER(WINED3D_RS_WRAP0), { STATE_RENDER(WINED3D_RS_WRAP0), state_wrap }, WINED3D_GL_EXT_NONE },
5062 { STATE_RENDER(WINED3D_RS_WRAP1), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5063 { STATE_RENDER(WINED3D_RS_WRAP2), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5064 { STATE_RENDER(WINED3D_RS_WRAP3), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5065 { STATE_RENDER(WINED3D_RS_WRAP4), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5066 { STATE_RENDER(WINED3D_RS_WRAP5), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5067 { STATE_RENDER(WINED3D_RS_WRAP6), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5068 { STATE_RENDER(WINED3D_RS_WRAP7), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5069 { STATE_RENDER(WINED3D_RS_WRAP8), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5070 { STATE_RENDER(WINED3D_RS_WRAP9), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5071 { STATE_RENDER(WINED3D_RS_WRAP10), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5072 { STATE_RENDER(WINED3D_RS_WRAP11), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5073 { STATE_RENDER(WINED3D_RS_WRAP12), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5074 { STATE_RENDER(WINED3D_RS_WRAP13), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5075 { STATE_RENDER(WINED3D_RS_WRAP14), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5076 { STATE_RENDER(WINED3D_RS_WRAP15), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE },
5077 { STATE_RENDER(WINED3D_RS_EXTENTS), { STATE_RENDER(WINED3D_RS_EXTENTS), state_extents }, WINED3D_GL_EXT_NONE },
5078 { STATE_RENDER(WINED3D_RS_COLORKEYBLENDENABLE), { STATE_RENDER(WINED3D_RS_COLORKEYBLENDENABLE), state_ckeyblend }, WINED3D_GL_EXT_NONE },
5079 { STATE_RENDER(WINED3D_RS_SOFTWAREVERTEXPROCESSING), { STATE_RENDER(WINED3D_RS_SOFTWAREVERTEXPROCESSING), state_swvp }, WINED3D_GL_EXT_NONE },
5080 { STATE_RENDER(WINED3D_RS_PATCHEDGESTYLE), { STATE_RENDER(WINED3D_RS_PATCHEDGESTYLE), state_patchedgestyle}, WINED3D_GL_EXT_NONE },
5081 { STATE_RENDER(WINED3D_RS_PATCHSEGMENTS), { STATE_RENDER(WINED3D_RS_PATCHSEGMENTS), state_patchsegments }, WINED3D_GL_EXT_NONE },
5082 { STATE_RENDER(WINED3D_RS_POSITIONDEGREE), { STATE_RENDER(WINED3D_RS_POSITIONDEGREE), state_positiondegree}, WINED3D_GL_EXT_NONE },
5083 { STATE_RENDER(WINED3D_RS_NORMALDEGREE), { STATE_RENDER(WINED3D_RS_NORMALDEGREE), state_normaldegree }, WINED3D_GL_EXT_NONE },
5084 { STATE_RENDER(WINED3D_RS_MINTESSELLATIONLEVEL), { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),NULL }, WINED3D_GL_EXT_NONE },
5085 { STATE_RENDER(WINED3D_RS_MAXTESSELLATIONLEVEL), { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),NULL }, WINED3D_GL_EXT_NONE },
5086 { STATE_RENDER(WINED3D_RS_ADAPTIVETESS_X), { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),NULL }, WINED3D_GL_EXT_NONE },
5087 { STATE_RENDER(WINED3D_RS_ADAPTIVETESS_Y), { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),NULL }, WINED3D_GL_EXT_NONE },
5088 { STATE_RENDER(WINED3D_RS_ADAPTIVETESS_Z), { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),NULL }, WINED3D_GL_EXT_NONE },
5089 { STATE_RENDER(WINED3D_RS_ADAPTIVETESS_W), { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),NULL }, WINED3D_GL_EXT_NONE },
5090 { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),{ STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),state_nvdb }, EXT_DEPTH_BOUNDS_TEST },
5091 { STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),{ STATE_RENDER(WINED3D_RS_ENABLEADAPTIVETESSELLATION),state_tessellation }, WINED3D_GL_EXT_NONE },
5092 { STATE_RENDER(WINED3D_RS_MULTISAMPLEANTIALIAS), { STATE_RENDER(WINED3D_RS_MULTISAMPLEANTIALIAS), state_msaa }, ARB_MULTISAMPLE },
5093 { STATE_RENDER(WINED3D_RS_MULTISAMPLEANTIALIAS), { STATE_RENDER(WINED3D_RS_MULTISAMPLEANTIALIAS), state_msaa_w }, WINED3D_GL_EXT_NONE },
5094 { STATE_RENDER(WINED3D_RS_MULTISAMPLEMASK), { STATE_RENDER(WINED3D_RS_MULTISAMPLEMASK), state_multisampmask }, WINED3D_GL_EXT_NONE },
5095 { STATE_RENDER(WINED3D_RS_DEBUGMONITORTOKEN), { STATE_RENDER(WINED3D_RS_DEBUGMONITORTOKEN), state_debug_monitor }, WINED3D_GL_EXT_NONE },
5096 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE), state_colorwrite0 }, EXT_DRAW_BUFFERS2 },
5097 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE), state_colorwrite }, WINED3D_GL_EXT_NONE },
5098 { STATE_RENDER(WINED3D_RS_BLENDOP), { STATE_RENDER(WINED3D_RS_BLENDOP), state_blendop }, EXT_BLEND_MINMAX },
5099 { STATE_RENDER(WINED3D_RS_BLENDOP), { STATE_RENDER(WINED3D_RS_BLENDOP), state_blendop_w }, WINED3D_GL_EXT_NONE },
5100 { STATE_RENDER(WINED3D_RS_SCISSORTESTENABLE), { STATE_RENDER(WINED3D_RS_SCISSORTESTENABLE), state_scissor }, WINED3D_GL_EXT_NONE },
5101 { STATE_RENDER(WINED3D_RS_SLOPESCALEDEPTHBIAS), { STATE_RENDER(WINED3D_RS_DEPTHBIAS), NULL }, WINED3D_GL_EXT_NONE },
5102 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE1), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE1), state_colorwrite1 }, EXT_DRAW_BUFFERS2 },
5103 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE1), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE), NULL }, WINED3D_GL_EXT_NONE },
5104 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE2), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE2), state_colorwrite2 }, EXT_DRAW_BUFFERS2 },
5105 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE2), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE), NULL }, WINED3D_GL_EXT_NONE },
5106 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE3), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE3), state_colorwrite3 }, EXT_DRAW_BUFFERS2 },
5107 { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE3), { STATE_RENDER(WINED3D_RS_COLORWRITEENABLE), NULL }, WINED3D_GL_EXT_NONE },
5108 { STATE_RENDER(WINED3D_RS_BLENDFACTOR), { STATE_RENDER(WINED3D_RS_BLENDFACTOR), state_blendfactor }, EXT_BLEND_COLOR },
5109 { STATE_RENDER(WINED3D_RS_BLENDFACTOR), { STATE_RENDER(WINED3D_RS_BLENDFACTOR), state_blendfactor_w }, WINED3D_GL_EXT_NONE },
5110 { STATE_RENDER(WINED3D_RS_DEPTHBIAS), { STATE_RENDER(WINED3D_RS_DEPTHBIAS), state_depthbias }, WINED3D_GL_EXT_NONE },
5111 { STATE_RENDER(WINED3D_RS_ZVISIBLE), { STATE_RENDER(WINED3D_RS_ZVISIBLE), state_zvisible }, WINED3D_GL_EXT_NONE },
5113 { STATE_SAMPLER(0), { STATE_SAMPLER(0), sampler }, WINED3D_GL_EXT_NONE },
5114 { STATE_SAMPLER(1), { STATE_SAMPLER(1), sampler }, WINED3D_GL_EXT_NONE },
5115 { STATE_SAMPLER(2), { STATE_SAMPLER(2), sampler }, WINED3D_GL_EXT_NONE },
5116 { STATE_SAMPLER(3), { STATE_SAMPLER(3), sampler }, WINED3D_GL_EXT_NONE },
5117 { STATE_SAMPLER(4), { STATE_SAMPLER(4), sampler }, WINED3D_GL_EXT_NONE },
5118 { STATE_SAMPLER(5), { STATE_SAMPLER(5), sampler }, WINED3D_GL_EXT_NONE },
5119 { STATE_SAMPLER(6), { STATE_SAMPLER(6), sampler }, WINED3D_GL_EXT_NONE },
5120 { STATE_SAMPLER(7), { STATE_SAMPLER(7), sampler }, WINED3D_GL_EXT_NONE },
5121 { STATE_SAMPLER(8), { STATE_SAMPLER(8), sampler }, WINED3D_GL_EXT_NONE },
5122 { STATE_SAMPLER(9), { STATE_SAMPLER(9), sampler }, WINED3D_GL_EXT_NONE },
5123 { STATE_SAMPLER(10), { STATE_SAMPLER(10), sampler }, WINED3D_GL_EXT_NONE },
5124 { STATE_SAMPLER(11), { STATE_SAMPLER(11), sampler }, WINED3D_GL_EXT_NONE },
5125 { STATE_SAMPLER(12), { STATE_SAMPLER(12), sampler }, WINED3D_GL_EXT_NONE },
5126 { STATE_SAMPLER(13), { STATE_SAMPLER(13), sampler }, WINED3D_GL_EXT_NONE },
5127 { STATE_SAMPLER(14), { STATE_SAMPLER(14), sampler }, WINED3D_GL_EXT_NONE },
5128 { STATE_SAMPLER(15), { STATE_SAMPLER(15), sampler }, WINED3D_GL_EXT_NONE },
5129 { STATE_SAMPLER(16), /* Vertex sampler 0 */ { STATE_SAMPLER(16), sampler }, WINED3D_GL_EXT_NONE },
5130 { STATE_SAMPLER(17), /* Vertex sampler 1 */ { STATE_SAMPLER(17), sampler }, WINED3D_GL_EXT_NONE },
5131 { STATE_SAMPLER(18), /* Vertex sampler 2 */ { STATE_SAMPLER(18), sampler }, WINED3D_GL_EXT_NONE },
5132 { STATE_SAMPLER(19), /* Vertex sampler 3 */ { STATE_SAMPLER(19), sampler }, WINED3D_GL_EXT_NONE },
5133 { STATE_BASEVERTEXINDEX, { STATE_BASEVERTEXINDEX, state_nop, }, ARB_DRAW_ELEMENTS_BASE_VERTEX },
5134 { STATE_BASEVERTEXINDEX, { STATE_STREAMSRC, NULL, }, WINED3D_GL_EXT_NONE },
5135 { STATE_FRAMEBUFFER, { STATE_FRAMEBUFFER, context_state_fb }, WINED3D_GL_EXT_NONE },
5136 { STATE_PIXELSHADER, { STATE_PIXELSHADER, context_state_drawbuf},WINED3D_GL_EXT_NONE },
5137 { STATE_GEOMETRY_SHADER, { STATE_GEOMETRY_SHADER, state_geometry_shader}, WINED3D_GL_EXT_NONE },
5138 {0 /* Terminate */, { 0, 0 }, WINED3D_GL_EXT_NONE },
5141 const struct StateEntryTemplate ffp_vertexstate_template[] = {
5142 { STATE_VDECL, { STATE_VDECL, vertexdeclaration }, WINED3D_GL_EXT_NONE },
5143 { STATE_VSHADER, { STATE_VDECL, NULL }, WINED3D_GL_EXT_NONE },
5144 { STATE_MATERIAL, { STATE_RENDER(WINED3D_RS_SPECULARENABLE), NULL }, WINED3D_GL_EXT_NONE },
5145 { STATE_RENDER(WINED3D_RS_SPECULARENABLE), { STATE_RENDER(WINED3D_RS_SPECULARENABLE), state_specularenable}, WINED3D_GL_EXT_NONE },
5147 { STATE_CLIPPLANE(0), { STATE_CLIPPLANE(0), clipplane }, WINED3D_GL_EXT_NONE },
5148 { STATE_CLIPPLANE(1), { STATE_CLIPPLANE(1), clipplane }, WINED3D_GL_EXT_NONE },
5149 { STATE_CLIPPLANE(2), { STATE_CLIPPLANE(2), clipplane }, WINED3D_GL_EXT_NONE },
5150 { STATE_CLIPPLANE(3), { STATE_CLIPPLANE(3), clipplane }, WINED3D_GL_EXT_NONE },
5151 { STATE_CLIPPLANE(4), { STATE_CLIPPLANE(4), clipplane }, WINED3D_GL_EXT_NONE },
5152 { STATE_CLIPPLANE(5), { STATE_CLIPPLANE(5), clipplane }, WINED3D_GL_EXT_NONE },
5153 { STATE_CLIPPLANE(6), { STATE_CLIPPLANE(6), clipplane }, WINED3D_GL_EXT_NONE },
5154 { STATE_CLIPPLANE(7), { STATE_CLIPPLANE(7), clipplane }, WINED3D_GL_EXT_NONE },
5155 { STATE_CLIPPLANE(8), { STATE_CLIPPLANE(8), clipplane }, WINED3D_GL_EXT_NONE },
5156 { STATE_CLIPPLANE(9), { STATE_CLIPPLANE(9), clipplane }, WINED3D_GL_EXT_NONE },
5157 { STATE_CLIPPLANE(10), { STATE_CLIPPLANE(10), clipplane }, WINED3D_GL_EXT_NONE },
5158 { STATE_CLIPPLANE(11), { STATE_CLIPPLANE(11), clipplane }, WINED3D_GL_EXT_NONE },
5159 { STATE_CLIPPLANE(12), { STATE_CLIPPLANE(12), clipplane }, WINED3D_GL_EXT_NONE },
5160 { STATE_CLIPPLANE(13), { STATE_CLIPPLANE(13), clipplane }, WINED3D_GL_EXT_NONE },
5161 { STATE_CLIPPLANE(14), { STATE_CLIPPLANE(14), clipplane }, WINED3D_GL_EXT_NONE },
5162 { STATE_CLIPPLANE(15), { STATE_CLIPPLANE(15), clipplane }, WINED3D_GL_EXT_NONE },
5163 { STATE_CLIPPLANE(16), { STATE_CLIPPLANE(16), clipplane }, WINED3D_GL_EXT_NONE },
5164 { STATE_CLIPPLANE(17), { STATE_CLIPPLANE(17), clipplane }, WINED3D_GL_EXT_NONE },
5165 { STATE_CLIPPLANE(18), { STATE_CLIPPLANE(18), clipplane }, WINED3D_GL_EXT_NONE },
5166 { STATE_CLIPPLANE(19), { STATE_CLIPPLANE(19), clipplane }, WINED3D_GL_EXT_NONE },
5167 { STATE_CLIPPLANE(20), { STATE_CLIPPLANE(20), clipplane }, WINED3D_GL_EXT_NONE },
5168 { STATE_CLIPPLANE(21), { STATE_CLIPPLANE(21), clipplane }, WINED3D_GL_EXT_NONE },
5169 { STATE_CLIPPLANE(22), { STATE_CLIPPLANE(22), clipplane }, WINED3D_GL_EXT_NONE },
5170 { STATE_CLIPPLANE(23), { STATE_CLIPPLANE(23), clipplane }, WINED3D_GL_EXT_NONE },
5171 { STATE_CLIPPLANE(24), { STATE_CLIPPLANE(24), clipplane }, WINED3D_GL_EXT_NONE },
5172 { STATE_CLIPPLANE(25), { STATE_CLIPPLANE(25), clipplane }, WINED3D_GL_EXT_NONE },
5173 { STATE_CLIPPLANE(26), { STATE_CLIPPLANE(26), clipplane }, WINED3D_GL_EXT_NONE },
5174 { STATE_CLIPPLANE(27), { STATE_CLIPPLANE(27), clipplane }, WINED3D_GL_EXT_NONE },
5175 { STATE_CLIPPLANE(28), { STATE_CLIPPLANE(28), clipplane }, WINED3D_GL_EXT_NONE },
5176 { STATE_CLIPPLANE(29), { STATE_CLIPPLANE(29), clipplane }, WINED3D_GL_EXT_NONE },
5177 { STATE_CLIPPLANE(30), { STATE_CLIPPLANE(30), clipplane }, WINED3D_GL_EXT_NONE },
5178 { STATE_CLIPPLANE(31), { STATE_CLIPPLANE(31), clipplane }, WINED3D_GL_EXT_NONE },
5180 { STATE_ACTIVELIGHT(0), { STATE_ACTIVELIGHT(0), light }, WINED3D_GL_EXT_NONE },
5181 { STATE_ACTIVELIGHT(1), { STATE_ACTIVELIGHT(1), light }, WINED3D_GL_EXT_NONE },
5182 { STATE_ACTIVELIGHT(2), { STATE_ACTIVELIGHT(2), light }, WINED3D_GL_EXT_NONE },
5183 { STATE_ACTIVELIGHT(3), { STATE_ACTIVELIGHT(3), light }, WINED3D_GL_EXT_NONE },
5184 { STATE_ACTIVELIGHT(4), { STATE_ACTIVELIGHT(4), light }, WINED3D_GL_EXT_NONE },
5185 { STATE_ACTIVELIGHT(5), { STATE_ACTIVELIGHT(5), light }, WINED3D_GL_EXT_NONE },
5186 { STATE_ACTIVELIGHT(6), { STATE_ACTIVELIGHT(6), light }, WINED3D_GL_EXT_NONE },
5187 { STATE_ACTIVELIGHT(7), { STATE_ACTIVELIGHT(7), light }, WINED3D_GL_EXT_NONE },
5189 { STATE_VIEWPORT, { STATE_VIEWPORT, viewport_vertexpart }, WINED3D_GL_EXT_NONE },
5190 /* Transform states follow */
5191 { STATE_TRANSFORM(WINED3D_TS_VIEW), { STATE_TRANSFORM(WINED3D_TS_VIEW), transform_view }, WINED3D_GL_EXT_NONE },
5192 { STATE_TRANSFORM(WINED3D_TS_PROJECTION), { STATE_TRANSFORM(WINED3D_TS_PROJECTION), transform_projection}, WINED3D_GL_EXT_NONE },
5193 { STATE_TRANSFORM(WINED3D_TS_TEXTURE0), { STATE_TEXTURESTAGE(0, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5194 { STATE_TRANSFORM(WINED3D_TS_TEXTURE1), { STATE_TEXTURESTAGE(1, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5195 { STATE_TRANSFORM(WINED3D_TS_TEXTURE2), { STATE_TEXTURESTAGE(2, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5196 { STATE_TRANSFORM(WINED3D_TS_TEXTURE3), { STATE_TEXTURESTAGE(3, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5197 { STATE_TRANSFORM(WINED3D_TS_TEXTURE4), { STATE_TEXTURESTAGE(4, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5198 { STATE_TRANSFORM(WINED3D_TS_TEXTURE5), { STATE_TEXTURESTAGE(5, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5199 { STATE_TRANSFORM(WINED3D_TS_TEXTURE6), { STATE_TEXTURESTAGE(6, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5200 { STATE_TRANSFORM(WINED3D_TS_TEXTURE7), { STATE_TEXTURESTAGE(7, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), NULL }, WINED3D_GL_EXT_NONE },
5201 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 0)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 0)), transform_world }, WINED3D_GL_EXT_NONE },
5202 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 1)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 1)), transform_worldex }, WINED3D_GL_EXT_NONE },
5203 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 2)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 2)), transform_worldex }, WINED3D_GL_EXT_NONE },
5204 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 3)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 3)), transform_worldex }, WINED3D_GL_EXT_NONE },
5205 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 4)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 4)), transform_worldex }, WINED3D_GL_EXT_NONE },
5206 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 5)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 5)), transform_worldex }, WINED3D_GL_EXT_NONE },
5207 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 6)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 6)), transform_worldex }, WINED3D_GL_EXT_NONE },
5208 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 7)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 7)), transform_worldex }, WINED3D_GL_EXT_NONE },
5209 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 8)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 8)), transform_worldex }, WINED3D_GL_EXT_NONE },
5210 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 9)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 9)), transform_worldex }, WINED3D_GL_EXT_NONE },
5211 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 10)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 10)), transform_worldex }, WINED3D_GL_EXT_NONE },
5212 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 11)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 11)), transform_worldex }, WINED3D_GL_EXT_NONE },
5213 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 12)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 12)), transform_worldex }, WINED3D_GL_EXT_NONE },
5214 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 13)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 13)), transform_worldex }, WINED3D_GL_EXT_NONE },
5215 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 14)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 14)), transform_worldex }, WINED3D_GL_EXT_NONE },
5216 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 15)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 15)), transform_worldex }, WINED3D_GL_EXT_NONE },
5217 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 16)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 16)), transform_worldex }, WINED3D_GL_EXT_NONE },
5218 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 17)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 17)), transform_worldex }, WINED3D_GL_EXT_NONE },
5219 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 18)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 18)), transform_worldex }, WINED3D_GL_EXT_NONE },
5220 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 19)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 19)), transform_worldex }, WINED3D_GL_EXT_NONE },
5221 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 20)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 20)), transform_worldex }, WINED3D_GL_EXT_NONE },
5222 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 21)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 21)), transform_worldex }, WINED3D_GL_EXT_NONE },
5223 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 22)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 22)), transform_worldex }, WINED3D_GL_EXT_NONE },
5224 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 23)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 23)), transform_worldex }, WINED3D_GL_EXT_NONE },
5225 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 24)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 24)), transform_worldex }, WINED3D_GL_EXT_NONE },
5226 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 25)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 25)), transform_worldex }, WINED3D_GL_EXT_NONE },
5227 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 26)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 26)), transform_worldex }, WINED3D_GL_EXT_NONE },
5228 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 27)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 27)), transform_worldex }, WINED3D_GL_EXT_NONE },
5229 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 28)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 28)), transform_worldex }, WINED3D_GL_EXT_NONE },
5230 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 29)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 29)), transform_worldex }, WINED3D_GL_EXT_NONE },
5231 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 30)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 30)), transform_worldex }, WINED3D_GL_EXT_NONE },
5232 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 31)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 31)), transform_worldex }, WINED3D_GL_EXT_NONE },
5233 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 32)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 32)), transform_worldex }, WINED3D_GL_EXT_NONE },
5234 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 33)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 33)), transform_worldex }, WINED3D_GL_EXT_NONE },
5235 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 34)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 34)), transform_worldex }, WINED3D_GL_EXT_NONE },
5236 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 35)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 35)), transform_worldex }, WINED3D_GL_EXT_NONE },
5237 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 36)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 36)), transform_worldex }, WINED3D_GL_EXT_NONE },
5238 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 37)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 37)), transform_worldex }, WINED3D_GL_EXT_NONE },
5239 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 38)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 38)), transform_worldex }, WINED3D_GL_EXT_NONE },
5240 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 39)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 39)), transform_worldex }, WINED3D_GL_EXT_NONE },
5241 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 40)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 40)), transform_worldex }, WINED3D_GL_EXT_NONE },
5242 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 41)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 41)), transform_worldex }, WINED3D_GL_EXT_NONE },
5243 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 42)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 42)), transform_worldex }, WINED3D_GL_EXT_NONE },
5244 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 43)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 43)), transform_worldex }, WINED3D_GL_EXT_NONE },
5245 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 44)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 44)), transform_worldex }, WINED3D_GL_EXT_NONE },
5246 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 45)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 45)), transform_worldex }, WINED3D_GL_EXT_NONE },
5247 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 46)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 46)), transform_worldex }, WINED3D_GL_EXT_NONE },
5248 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 47)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 47)), transform_worldex }, WINED3D_GL_EXT_NONE },
5249 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 48)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 48)), transform_worldex }, WINED3D_GL_EXT_NONE },
5250 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 49)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 49)), transform_worldex }, WINED3D_GL_EXT_NONE },
5251 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 50)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 50)), transform_worldex }, WINED3D_GL_EXT_NONE },
5252 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 51)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 51)), transform_worldex }, WINED3D_GL_EXT_NONE },
5253 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 52)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 52)), transform_worldex }, WINED3D_GL_EXT_NONE },
5254 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 53)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 53)), transform_worldex }, WINED3D_GL_EXT_NONE },
5255 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 54)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 54)), transform_worldex }, WINED3D_GL_EXT_NONE },
5256 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 55)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 55)), transform_worldex }, WINED3D_GL_EXT_NONE },
5257 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 56)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 56)), transform_worldex }, WINED3D_GL_EXT_NONE },
5258 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 57)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 57)), transform_worldex }, WINED3D_GL_EXT_NONE },
5259 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 58)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 58)), transform_worldex }, WINED3D_GL_EXT_NONE },
5260 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 59)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 59)), transform_worldex }, WINED3D_GL_EXT_NONE },
5261 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 60)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 60)), transform_worldex }, WINED3D_GL_EXT_NONE },
5262 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 61)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 61)), transform_worldex }, WINED3D_GL_EXT_NONE },
5263 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 62)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 62)), transform_worldex }, WINED3D_GL_EXT_NONE },
5264 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 63)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 63)), transform_worldex }, WINED3D_GL_EXT_NONE },
5265 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 64)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 64)), transform_worldex }, WINED3D_GL_EXT_NONE },
5266 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 65)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 65)), transform_worldex }, WINED3D_GL_EXT_NONE },
5267 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 66)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 66)), transform_worldex }, WINED3D_GL_EXT_NONE },
5268 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 67)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 67)), transform_worldex }, WINED3D_GL_EXT_NONE },
5269 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 68)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 68)), transform_worldex }, WINED3D_GL_EXT_NONE },
5270 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 69)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 69)), transform_worldex }, WINED3D_GL_EXT_NONE },
5271 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 70)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 70)), transform_worldex }, WINED3D_GL_EXT_NONE },
5272 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 71)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 71)), transform_worldex }, WINED3D_GL_EXT_NONE },
5273 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 72)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 72)), transform_worldex }, WINED3D_GL_EXT_NONE },
5274 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 73)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 73)), transform_worldex }, WINED3D_GL_EXT_NONE },
5275 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 74)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 74)), transform_worldex }, WINED3D_GL_EXT_NONE },
5276 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 75)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 75)), transform_worldex }, WINED3D_GL_EXT_NONE },
5277 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 76)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 76)), transform_worldex }, WINED3D_GL_EXT_NONE },
5278 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 77)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 77)), transform_worldex }, WINED3D_GL_EXT_NONE },
5279 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 78)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 78)), transform_worldex }, WINED3D_GL_EXT_NONE },
5280 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 79)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 79)), transform_worldex }, WINED3D_GL_EXT_NONE },
5281 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 80)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 80)), transform_worldex }, WINED3D_GL_EXT_NONE },
5282 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 81)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 81)), transform_worldex }, WINED3D_GL_EXT_NONE },
5283 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 82)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 82)), transform_worldex }, WINED3D_GL_EXT_NONE },
5284 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 83)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 83)), transform_worldex }, WINED3D_GL_EXT_NONE },
5285 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 84)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 84)), transform_worldex }, WINED3D_GL_EXT_NONE },
5286 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 85)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 85)), transform_worldex }, WINED3D_GL_EXT_NONE },
5287 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 86)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 86)), transform_worldex }, WINED3D_GL_EXT_NONE },
5288 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 87)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 87)), transform_worldex }, WINED3D_GL_EXT_NONE },
5289 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 88)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 88)), transform_worldex }, WINED3D_GL_EXT_NONE },
5290 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 89)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 89)), transform_worldex }, WINED3D_GL_EXT_NONE },
5291 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 90)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 90)), transform_worldex }, WINED3D_GL_EXT_NONE },
5292 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 91)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 91)), transform_worldex }, WINED3D_GL_EXT_NONE },
5293 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 92)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 92)), transform_worldex }, WINED3D_GL_EXT_NONE },
5294 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 93)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 93)), transform_worldex }, WINED3D_GL_EXT_NONE },
5295 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 94)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 94)), transform_worldex }, WINED3D_GL_EXT_NONE },
5296 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 95)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 95)), transform_worldex }, WINED3D_GL_EXT_NONE },
5297 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 96)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 96)), transform_worldex }, WINED3D_GL_EXT_NONE },
5298 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 97)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 97)), transform_worldex }, WINED3D_GL_EXT_NONE },
5299 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 98)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 98)), transform_worldex }, WINED3D_GL_EXT_NONE },
5300 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 99)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX( 99)), transform_worldex }, WINED3D_GL_EXT_NONE },
5301 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(100)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(100)), transform_worldex }, WINED3D_GL_EXT_NONE },
5302 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(101)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(101)), transform_worldex }, WINED3D_GL_EXT_NONE },
5303 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(102)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(102)), transform_worldex }, WINED3D_GL_EXT_NONE },
5304 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(103)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(103)), transform_worldex }, WINED3D_GL_EXT_NONE },
5305 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(104)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(104)), transform_worldex }, WINED3D_GL_EXT_NONE },
5306 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(105)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(105)), transform_worldex }, WINED3D_GL_EXT_NONE },
5307 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(106)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(106)), transform_worldex }, WINED3D_GL_EXT_NONE },
5308 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(107)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(107)), transform_worldex }, WINED3D_GL_EXT_NONE },
5309 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(108)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(108)), transform_worldex }, WINED3D_GL_EXT_NONE },
5310 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(109)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(109)), transform_worldex }, WINED3D_GL_EXT_NONE },
5311 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(110)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(110)), transform_worldex }, WINED3D_GL_EXT_NONE },
5312 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(111)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(111)), transform_worldex }, WINED3D_GL_EXT_NONE },
5313 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(112)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(112)), transform_worldex }, WINED3D_GL_EXT_NONE },
5314 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(113)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(113)), transform_worldex }, WINED3D_GL_EXT_NONE },
5315 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(114)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(114)), transform_worldex }, WINED3D_GL_EXT_NONE },
5316 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(115)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(115)), transform_worldex }, WINED3D_GL_EXT_NONE },
5317 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(116)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(116)), transform_worldex }, WINED3D_GL_EXT_NONE },
5318 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(117)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(117)), transform_worldex }, WINED3D_GL_EXT_NONE },
5319 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(118)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(118)), transform_worldex }, WINED3D_GL_EXT_NONE },
5320 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(119)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(119)), transform_worldex }, WINED3D_GL_EXT_NONE },
5321 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(120)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(120)), transform_worldex }, WINED3D_GL_EXT_NONE },
5322 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(121)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(121)), transform_worldex }, WINED3D_GL_EXT_NONE },
5323 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(122)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(122)), transform_worldex }, WINED3D_GL_EXT_NONE },
5324 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(123)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(123)), transform_worldex }, WINED3D_GL_EXT_NONE },
5325 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(124)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(124)), transform_worldex }, WINED3D_GL_EXT_NONE },
5326 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(125)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(125)), transform_worldex }, WINED3D_GL_EXT_NONE },
5327 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(126)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(126)), transform_worldex }, WINED3D_GL_EXT_NONE },
5328 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(127)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(127)), transform_worldex }, WINED3D_GL_EXT_NONE },
5329 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(128)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(128)), transform_worldex }, WINED3D_GL_EXT_NONE },
5330 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(129)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(129)), transform_worldex }, WINED3D_GL_EXT_NONE },
5331 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(130)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(130)), transform_worldex }, WINED3D_GL_EXT_NONE },
5332 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(131)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(131)), transform_worldex }, WINED3D_GL_EXT_NONE },
5333 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(132)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(132)), transform_worldex }, WINED3D_GL_EXT_NONE },
5334 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(133)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(133)), transform_worldex }, WINED3D_GL_EXT_NONE },
5335 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(134)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(134)), transform_worldex }, WINED3D_GL_EXT_NONE },
5336 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(135)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(135)), transform_worldex }, WINED3D_GL_EXT_NONE },
5337 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(136)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(136)), transform_worldex }, WINED3D_GL_EXT_NONE },
5338 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(137)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(137)), transform_worldex }, WINED3D_GL_EXT_NONE },
5339 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(138)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(138)), transform_worldex }, WINED3D_GL_EXT_NONE },
5340 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(139)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(139)), transform_worldex }, WINED3D_GL_EXT_NONE },
5341 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(140)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(140)), transform_worldex }, WINED3D_GL_EXT_NONE },
5342 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(141)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(141)), transform_worldex }, WINED3D_GL_EXT_NONE },
5343 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(142)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(142)), transform_worldex }, WINED3D_GL_EXT_NONE },
5344 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(143)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(143)), transform_worldex }, WINED3D_GL_EXT_NONE },
5345 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(144)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(144)), transform_worldex }, WINED3D_GL_EXT_NONE },
5346 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(145)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(145)), transform_worldex }, WINED3D_GL_EXT_NONE },
5347 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(146)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(146)), transform_worldex }, WINED3D_GL_EXT_NONE },
5348 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(147)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(147)), transform_worldex }, WINED3D_GL_EXT_NONE },
5349 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(148)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(148)), transform_worldex }, WINED3D_GL_EXT_NONE },
5350 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(149)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(149)), transform_worldex }, WINED3D_GL_EXT_NONE },
5351 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(150)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(150)), transform_worldex }, WINED3D_GL_EXT_NONE },
5352 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(151)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(151)), transform_worldex }, WINED3D_GL_EXT_NONE },
5353 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(152)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(152)), transform_worldex }, WINED3D_GL_EXT_NONE },
5354 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(153)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(153)), transform_worldex }, WINED3D_GL_EXT_NONE },
5355 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(154)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(154)), transform_worldex }, WINED3D_GL_EXT_NONE },
5356 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(155)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(155)), transform_worldex }, WINED3D_GL_EXT_NONE },
5357 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(156)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(156)), transform_worldex }, WINED3D_GL_EXT_NONE },
5358 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(157)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(157)), transform_worldex }, WINED3D_GL_EXT_NONE },
5359 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(158)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(158)), transform_worldex }, WINED3D_GL_EXT_NONE },
5360 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(159)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(159)), transform_worldex }, WINED3D_GL_EXT_NONE },
5361 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(160)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(160)), transform_worldex }, WINED3D_GL_EXT_NONE },
5362 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(161)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(161)), transform_worldex }, WINED3D_GL_EXT_NONE },
5363 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(162)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(162)), transform_worldex }, WINED3D_GL_EXT_NONE },
5364 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(163)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(163)), transform_worldex }, WINED3D_GL_EXT_NONE },
5365 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(164)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(164)), transform_worldex }, WINED3D_GL_EXT_NONE },
5366 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(165)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(165)), transform_worldex }, WINED3D_GL_EXT_NONE },
5367 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(166)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(166)), transform_worldex }, WINED3D_GL_EXT_NONE },
5368 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(167)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(167)), transform_worldex }, WINED3D_GL_EXT_NONE },
5369 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(168)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(168)), transform_worldex }, WINED3D_GL_EXT_NONE },
5370 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(169)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(169)), transform_worldex }, WINED3D_GL_EXT_NONE },
5371 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(170)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(170)), transform_worldex }, WINED3D_GL_EXT_NONE },
5372 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(171)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(171)), transform_worldex }, WINED3D_GL_EXT_NONE },
5373 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(172)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(172)), transform_worldex }, WINED3D_GL_EXT_NONE },
5374 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(173)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(173)), transform_worldex }, WINED3D_GL_EXT_NONE },
5375 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(174)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(174)), transform_worldex }, WINED3D_GL_EXT_NONE },
5376 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(175)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(175)), transform_worldex }, WINED3D_GL_EXT_NONE },
5377 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(176)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(176)), transform_worldex }, WINED3D_GL_EXT_NONE },
5378 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(177)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(177)), transform_worldex }, WINED3D_GL_EXT_NONE },
5379 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(178)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(178)), transform_worldex }, WINED3D_GL_EXT_NONE },
5380 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(179)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(179)), transform_worldex }, WINED3D_GL_EXT_NONE },
5381 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(180)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(180)), transform_worldex }, WINED3D_GL_EXT_NONE },
5382 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(181)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(181)), transform_worldex }, WINED3D_GL_EXT_NONE },
5383 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(182)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(182)), transform_worldex }, WINED3D_GL_EXT_NONE },
5384 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(183)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(183)), transform_worldex }, WINED3D_GL_EXT_NONE },
5385 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(184)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(184)), transform_worldex }, WINED3D_GL_EXT_NONE },
5386 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(185)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(185)), transform_worldex }, WINED3D_GL_EXT_NONE },
5387 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(186)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(186)), transform_worldex }, WINED3D_GL_EXT_NONE },
5388 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(187)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(187)), transform_worldex }, WINED3D_GL_EXT_NONE },
5389 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(188)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(188)), transform_worldex }, WINED3D_GL_EXT_NONE },
5390 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(189)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(189)), transform_worldex }, WINED3D_GL_EXT_NONE },
5391 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(190)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(190)), transform_worldex }, WINED3D_GL_EXT_NONE },
5392 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(191)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(191)), transform_worldex }, WINED3D_GL_EXT_NONE },
5393 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(192)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(192)), transform_worldex }, WINED3D_GL_EXT_NONE },
5394 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(193)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(193)), transform_worldex }, WINED3D_GL_EXT_NONE },
5395 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(194)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(194)), transform_worldex }, WINED3D_GL_EXT_NONE },
5396 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(195)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(195)), transform_worldex }, WINED3D_GL_EXT_NONE },
5397 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(196)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(196)), transform_worldex }, WINED3D_GL_EXT_NONE },
5398 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(197)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(197)), transform_worldex }, WINED3D_GL_EXT_NONE },
5399 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(198)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(198)), transform_worldex }, WINED3D_GL_EXT_NONE },
5400 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(199)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(199)), transform_worldex }, WINED3D_GL_EXT_NONE },
5401 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(200)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(200)), transform_worldex }, WINED3D_GL_EXT_NONE },
5402 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(201)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(201)), transform_worldex }, WINED3D_GL_EXT_NONE },
5403 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(202)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(202)), transform_worldex }, WINED3D_GL_EXT_NONE },
5404 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(203)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(203)), transform_worldex }, WINED3D_GL_EXT_NONE },
5405 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(204)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(204)), transform_worldex }, WINED3D_GL_EXT_NONE },
5406 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(205)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(205)), transform_worldex }, WINED3D_GL_EXT_NONE },
5407 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(206)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(206)), transform_worldex }, WINED3D_GL_EXT_NONE },
5408 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(207)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(207)), transform_worldex }, WINED3D_GL_EXT_NONE },
5409 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(208)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(208)), transform_worldex }, WINED3D_GL_EXT_NONE },
5410 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(209)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(209)), transform_worldex }, WINED3D_GL_EXT_NONE },
5411 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(210)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(210)), transform_worldex }, WINED3D_GL_EXT_NONE },
5412 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(211)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(211)), transform_worldex }, WINED3D_GL_EXT_NONE },
5413 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(212)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(212)), transform_worldex }, WINED3D_GL_EXT_NONE },
5414 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(213)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(213)), transform_worldex }, WINED3D_GL_EXT_NONE },
5415 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(214)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(214)), transform_worldex }, WINED3D_GL_EXT_NONE },
5416 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(215)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(215)), transform_worldex }, WINED3D_GL_EXT_NONE },
5417 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(216)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(216)), transform_worldex }, WINED3D_GL_EXT_NONE },
5418 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(217)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(217)), transform_worldex }, WINED3D_GL_EXT_NONE },
5419 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(218)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(218)), transform_worldex }, WINED3D_GL_EXT_NONE },
5420 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(219)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(219)), transform_worldex }, WINED3D_GL_EXT_NONE },
5421 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(220)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(220)), transform_worldex }, WINED3D_GL_EXT_NONE },
5422 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(221)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(221)), transform_worldex }, WINED3D_GL_EXT_NONE },
5423 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(222)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(222)), transform_worldex }, WINED3D_GL_EXT_NONE },
5424 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(223)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(223)), transform_worldex }, WINED3D_GL_EXT_NONE },
5425 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(224)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(224)), transform_worldex }, WINED3D_GL_EXT_NONE },
5426 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(225)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(225)), transform_worldex }, WINED3D_GL_EXT_NONE },
5427 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(226)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(226)), transform_worldex }, WINED3D_GL_EXT_NONE },
5428 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(227)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(227)), transform_worldex }, WINED3D_GL_EXT_NONE },
5429 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(228)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(228)), transform_worldex }, WINED3D_GL_EXT_NONE },
5430 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(229)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(229)), transform_worldex }, WINED3D_GL_EXT_NONE },
5431 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(230)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(230)), transform_worldex }, WINED3D_GL_EXT_NONE },
5432 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(231)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(231)), transform_worldex }, WINED3D_GL_EXT_NONE },
5433 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(232)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(232)), transform_worldex }, WINED3D_GL_EXT_NONE },
5434 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(233)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(233)), transform_worldex }, WINED3D_GL_EXT_NONE },
5435 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(234)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(234)), transform_worldex }, WINED3D_GL_EXT_NONE },
5436 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(235)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(235)), transform_worldex }, WINED3D_GL_EXT_NONE },
5437 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(236)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(236)), transform_worldex }, WINED3D_GL_EXT_NONE },
5438 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(237)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(237)), transform_worldex }, WINED3D_GL_EXT_NONE },
5439 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(238)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(238)), transform_worldex }, WINED3D_GL_EXT_NONE },
5440 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(239)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(239)), transform_worldex }, WINED3D_GL_EXT_NONE },
5441 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(240)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(240)), transform_worldex }, WINED3D_GL_EXT_NONE },
5442 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(241)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(241)), transform_worldex }, WINED3D_GL_EXT_NONE },
5443 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(242)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(242)), transform_worldex }, WINED3D_GL_EXT_NONE },
5444 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(243)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(243)), transform_worldex }, WINED3D_GL_EXT_NONE },
5445 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(244)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(244)), transform_worldex }, WINED3D_GL_EXT_NONE },
5446 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(245)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(245)), transform_worldex }, WINED3D_GL_EXT_NONE },
5447 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(246)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(246)), transform_worldex }, WINED3D_GL_EXT_NONE },
5448 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(247)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(247)), transform_worldex }, WINED3D_GL_EXT_NONE },
5449 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(248)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(248)), transform_worldex }, WINED3D_GL_EXT_NONE },
5450 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(249)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(249)), transform_worldex }, WINED3D_GL_EXT_NONE },
5451 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(250)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(250)), transform_worldex }, WINED3D_GL_EXT_NONE },
5452 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(251)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(251)), transform_worldex }, WINED3D_GL_EXT_NONE },
5453 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(252)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(252)), transform_worldex }, WINED3D_GL_EXT_NONE },
5454 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(253)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(253)), transform_worldex }, WINED3D_GL_EXT_NONE },
5455 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(254)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(254)), transform_worldex }, WINED3D_GL_EXT_NONE },
5456 { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(255)), { STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(255)), transform_worldex }, WINED3D_GL_EXT_NONE },
5457 { STATE_TEXTURESTAGE(0, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(0, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5458 { STATE_TEXTURESTAGE(1, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(1, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5459 { STATE_TEXTURESTAGE(2, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(2, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5460 { STATE_TEXTURESTAGE(3, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(3, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5461 { STATE_TEXTURESTAGE(4, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(4, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5462 { STATE_TEXTURESTAGE(5, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(5, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5463 { STATE_TEXTURESTAGE(6, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(6, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5464 { STATE_TEXTURESTAGE(7, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), {STATE_TEXTURESTAGE(7, WINED3D_TSS_TEXTURE_TRANSFORM_FLAGS), transform_texture }, WINED3D_GL_EXT_NONE },
5465 { STATE_TEXTURESTAGE(0, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(0, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5466 { STATE_TEXTURESTAGE(1, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(1, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5467 { STATE_TEXTURESTAGE(2, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(2, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5468 { STATE_TEXTURESTAGE(3, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(3, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5469 { STATE_TEXTURESTAGE(4, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(4, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5470 { STATE_TEXTURESTAGE(5, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(5, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5471 { STATE_TEXTURESTAGE(6, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(6, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5472 { STATE_TEXTURESTAGE(7, WINED3D_TSS_TEXCOORD_INDEX), { STATE_TEXTURESTAGE(7, WINED3D_TSS_TEXCOORD_INDEX), tex_coordindex }, WINED3D_GL_EXT_NONE },
5474 { STATE_RENDER(WINED3D_RS_FOGENABLE), { STATE_RENDER(WINED3D_RS_FOGENABLE), state_fog_vertexpart}, WINED3D_GL_EXT_NONE },
5475 { STATE_RENDER(WINED3D_RS_FOGTABLEMODE), { STATE_RENDER(WINED3D_RS_FOGENABLE), NULL }, WINED3D_GL_EXT_NONE },
5476 { STATE_RENDER(WINED3D_RS_FOGVERTEXMODE), { STATE_RENDER(WINED3D_RS_FOGENABLE), NULL }, WINED3D_GL_EXT_NONE },
5477 { STATE_RENDER(WINED3D_RS_RANGEFOGENABLE), { STATE_RENDER(WINED3D_RS_FOGENABLE), NULL }, WINED3D_GL_EXT_NONE },
5478 { STATE_RENDER(WINED3D_RS_CLIPPING), { STATE_RENDER(WINED3D_RS_CLIPPING), state_clipping }, WINED3D_GL_EXT_NONE },
5479 { STATE_RENDER(WINED3D_RS_CLIPPLANEENABLE), { STATE_RENDER(WINED3D_RS_CLIPPING), NULL }, WINED3D_GL_EXT_NONE },
5480 { STATE_RENDER(WINED3D_RS_LIGHTING), { STATE_RENDER(WINED3D_RS_LIGHTING), state_lighting }, WINED3D_GL_EXT_NONE },
5481 { STATE_RENDER(WINED3D_RS_AMBIENT), { STATE_RENDER(WINED3D_RS_AMBIENT), state_ambient }, WINED3D_GL_EXT_NONE },
5482 { STATE_RENDER(WINED3D_RS_COLORVERTEX), { STATE_RENDER(WINED3D_RS_COLORVERTEX), state_colormat }, WINED3D_GL_EXT_NONE },
5483 { STATE_RENDER(WINED3D_RS_LOCALVIEWER), { STATE_RENDER(WINED3D_RS_LOCALVIEWER), state_localviewer }, WINED3D_GL_EXT_NONE },
5484 { STATE_RENDER(WINED3D_RS_NORMALIZENORMALS), { STATE_RENDER(WINED3D_RS_NORMALIZENORMALS), state_normalize }, WINED3D_GL_EXT_NONE },
5485 { STATE_RENDER(WINED3D_RS_DIFFUSEMATERIALSOURCE), { STATE_RENDER(WINED3D_RS_COLORVERTEX), NULL }, WINED3D_GL_EXT_NONE },
5486 { STATE_RENDER(WINED3D_RS_SPECULARMATERIALSOURCE), { STATE_RENDER(WINED3D_RS_COLORVERTEX), NULL }, WINED3D_GL_EXT_NONE },
5487 { STATE_RENDER(WINED3D_RS_AMBIENTMATERIALSOURCE), { STATE_RENDER(WINED3D_RS_COLORVERTEX), NULL }, WINED3D_GL_EXT_NONE },
5488 { STATE_RENDER(WINED3D_RS_EMISSIVEMATERIALSOURCE), { STATE_RENDER(WINED3D_RS_COLORVERTEX), NULL }, WINED3D_GL_EXT_NONE },
5489 { STATE_RENDER(WINED3D_RS_VERTEXBLEND), { STATE_RENDER(WINED3D_RS_VERTEXBLEND), state_vertexblend }, ARB_VERTEX_BLEND },
5490 { STATE_RENDER(WINED3D_RS_VERTEXBLEND), { STATE_RENDER(WINED3D_RS_VERTEXBLEND), state_vertexblend_w }, WINED3D_GL_EXT_NONE },
5491 { STATE_RENDER(WINED3D_RS_POINTSIZE), { STATE_RENDER(WINED3D_RS_POINTSCALEENABLE), NULL }, WINED3D_GL_EXT_NONE },
5492 { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), state_psizemin_arb }, ARB_POINT_PARAMETERS },
5493 { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), state_psizemin_ext }, EXT_POINT_PARAMETERS },
5494 { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), state_psizemin_w }, WINED3D_GL_EXT_NONE },
5495 { STATE_RENDER(WINED3D_RS_POINTSPRITEENABLE), { STATE_RENDER(WINED3D_RS_POINTSPRITEENABLE), state_pointsprite }, ARB_POINT_SPRITE },
5496 { STATE_RENDER(WINED3D_RS_POINTSPRITEENABLE), { STATE_RENDER(WINED3D_RS_POINTSPRITEENABLE), state_pointsprite_w }, WINED3D_GL_EXT_NONE },
5497 { STATE_RENDER(WINED3D_RS_POINTSCALEENABLE), { STATE_RENDER(WINED3D_RS_POINTSCALEENABLE), state_pscale }, WINED3D_GL_EXT_NONE },
5498 { STATE_RENDER(WINED3D_RS_POINTSCALE_A), { STATE_RENDER(WINED3D_RS_POINTSCALEENABLE), NULL }, WINED3D_GL_EXT_NONE },
5499 { STATE_RENDER(WINED3D_RS_POINTSCALE_B), { STATE_RENDER(WINED3D_RS_POINTSCALEENABLE), NULL }, WINED3D_GL_EXT_NONE },
5500 { STATE_RENDER(WINED3D_RS_POINTSCALE_C), { STATE_RENDER(WINED3D_RS_POINTSCALEENABLE), NULL }, WINED3D_GL_EXT_NONE },
5501 { STATE_RENDER(WINED3D_RS_POINTSIZE_MAX), { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), NULL }, ARB_POINT_PARAMETERS },
5502 { STATE_RENDER(WINED3D_RS_POINTSIZE_MAX), { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), NULL }, EXT_POINT_PARAMETERS },
5503 { STATE_RENDER(WINED3D_RS_POINTSIZE_MAX), { STATE_RENDER(WINED3D_RS_POINTSIZE_MIN), NULL }, WINED3D_GL_EXT_NONE },
5504 { STATE_RENDER(WINED3D_RS_TWEENFACTOR), { STATE_RENDER(WINED3D_RS_VERTEXBLEND), NULL }, WINED3D_GL_EXT_NONE },
5505 { STATE_RENDER(WINED3D_RS_INDEXEDVERTEXBLENDENABLE), { STATE_RENDER(WINED3D_RS_VERTEXBLEND), NULL }, WINED3D_GL_EXT_NONE },
5507 /* Samplers for NP2 texture matrix adjustions. They are not needed if GL_ARB_texture_non_power_of_two is supported,
5508 * so register a NULL state handler in that case to get the vertex part of sampler() skipped(VTF is handled in the misc states.
5509 * otherwise, register sampler_texmatrix, which takes care of updating the texture matrix
5511 { STATE_SAMPLER(0), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5512 { STATE_SAMPLER(0), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5513 { STATE_SAMPLER(0), { STATE_SAMPLER(0), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5514 { STATE_SAMPLER(1), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5515 { STATE_SAMPLER(1), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5516 { STATE_SAMPLER(1), { STATE_SAMPLER(1), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5517 { STATE_SAMPLER(2), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5518 { STATE_SAMPLER(2), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5519 { STATE_SAMPLER(2), { STATE_SAMPLER(2), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5520 { STATE_SAMPLER(3), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5521 { STATE_SAMPLER(3), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5522 { STATE_SAMPLER(3), { STATE_SAMPLER(3), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5523 { STATE_SAMPLER(4), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5524 { STATE_SAMPLER(4), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5525 { STATE_SAMPLER(4), { STATE_SAMPLER(4), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5526 { STATE_SAMPLER(5), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5527 { STATE_SAMPLER(5), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5528 { STATE_SAMPLER(5), { STATE_SAMPLER(5), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5529 { STATE_SAMPLER(6), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5530 { STATE_SAMPLER(6), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5531 { STATE_SAMPLER(6), { STATE_SAMPLER(6), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5532 { STATE_SAMPLER(7), { 0, NULL }, ARB_TEXTURE_NON_POWER_OF_TWO },
5533 { STATE_SAMPLER(7), { 0, NULL }, WINED3D_GL_NORMALIZED_TEXRECT },
5534 { STATE_SAMPLER(7), { STATE_SAMPLER(7), sampler_texmatrix }, WINED3D_GL_EXT_NONE },
5535 {0 /* Terminate */, { 0, 0 }, WINED3D_GL_EXT_NONE },
5538 static const struct StateEntryTemplate ffp_fragmentstate_template[] = {
5539 { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5540 { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5541 { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5542 { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5543 { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5544 { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5545 { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5546 { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(0, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5547 { STATE_TEXTURESTAGE(0, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(0, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5548 { STATE_TEXTURESTAGE(0, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5549 { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5550 { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5551 { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5552 { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5553 { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5554 { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5555 { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5556 { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(1, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5557 { STATE_TEXTURESTAGE(1, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(1, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5558 { STATE_TEXTURESTAGE(1, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5559 { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5560 { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5561 { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5562 { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5563 { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5564 { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5565 { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5566 { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(2, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5567 { STATE_TEXTURESTAGE(2, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(2, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5568 { STATE_TEXTURESTAGE(2, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5569 { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5570 { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5571 { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5572 { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5573 { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5574 { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5575 { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5576 { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(3, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5577 { STATE_TEXTURESTAGE(3, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(3, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5578 { STATE_TEXTURESTAGE(3, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5579 { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5580 { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5581 { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5582 { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5583 { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5584 { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5585 { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5586 { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(4, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5587 { STATE_TEXTURESTAGE(4, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(4, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5588 { STATE_TEXTURESTAGE(4, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5589 { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5590 { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5591 { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5592 { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5593 { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5594 { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5595 { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5596 { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(5, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5597 { STATE_TEXTURESTAGE(5, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(5, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5598 { STATE_TEXTURESTAGE(5, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5599 { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5600 { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5601 { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5602 { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5603 { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5604 { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5605 { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5606 { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(6, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5607 { STATE_TEXTURESTAGE(6, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(6, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5608 { STATE_TEXTURESTAGE(6, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5609 { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_OP), { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_OP), tex_colorop }, WINED3D_GL_EXT_NONE },
5610 { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_ARG1), { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5611 { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_ARG2), { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5612 { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_OP), { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_OP), tex_alphaop }, WINED3D_GL_EXT_NONE },
5613 { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_ARG1), { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5614 { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_ARG2), { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5615 { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_ARG0), { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5616 { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_ARG0), { STATE_TEXTURESTAGE(7, WINED3D_TSS_ALPHA_OP), NULL }, WINED3D_GL_EXT_NONE },
5617 { STATE_TEXTURESTAGE(7, WINED3D_TSS_RESULT_ARG), { STATE_TEXTURESTAGE(7, WINED3D_TSS_COLOR_OP), NULL }, WINED3D_GL_EXT_NONE },
5618 { STATE_TEXTURESTAGE(7, WINED3D_TSS_CONSTANT), { 0 /* As long as we don't support D3DTA_CONSTANT */, NULL }, WINED3D_GL_EXT_NONE },
5619 { STATE_PIXELSHADER, { STATE_PIXELSHADER, apply_pixelshader }, WINED3D_GL_EXT_NONE },
5620 { STATE_RENDER(WINED3D_RS_SRGBWRITEENABLE), { STATE_PIXELSHADER, NULL }, WINED3D_GL_EXT_NONE },
5621 { STATE_RENDER(WINED3D_RS_TEXTUREFACTOR), { STATE_RENDER(WINED3D_RS_TEXTUREFACTOR), state_texfactor }, WINED3D_GL_EXT_NONE },
5622 { STATE_RENDER(WINED3D_RS_FOGCOLOR), { STATE_RENDER(WINED3D_RS_FOGCOLOR), state_fogcolor }, WINED3D_GL_EXT_NONE },
5623 { STATE_RENDER(WINED3D_RS_FOGDENSITY), { STATE_RENDER(WINED3D_RS_FOGDENSITY), state_fogdensity }, WINED3D_GL_EXT_NONE },
5624 { STATE_RENDER(WINED3D_RS_FOGENABLE), { STATE_RENDER(WINED3D_RS_FOGENABLE), state_fog_fragpart }, WINED3D_GL_EXT_NONE },
5625 { STATE_RENDER(WINED3D_RS_FOGTABLEMODE), { STATE_RENDER(WINED3D_RS_FOGENABLE), NULL }, WINED3D_GL_EXT_NONE },
5626 { STATE_RENDER(WINED3D_RS_FOGVERTEXMODE), { STATE_RENDER(WINED3D_RS_FOGENABLE), NULL }, WINED3D_GL_EXT_NONE },
5627 { STATE_RENDER(WINED3D_RS_FOGSTART), { STATE_RENDER(WINED3D_RS_FOGSTART), state_fogstartend }, WINED3D_GL_EXT_NONE },
5628 { STATE_RENDER(WINED3D_RS_FOGEND), { STATE_RENDER(WINED3D_RS_FOGSTART), NULL }, WINED3D_GL_EXT_NONE },
5629 { STATE_SAMPLER(0), { STATE_SAMPLER(0), sampler_texdim }, WINED3D_GL_EXT_NONE },
5630 { STATE_SAMPLER(1), { STATE_SAMPLER(1), sampler_texdim }, WINED3D_GL_EXT_NONE },
5631 { STATE_SAMPLER(2), { STATE_SAMPLER(2), sampler_texdim }, WINED3D_GL_EXT_NONE },
5632 { STATE_SAMPLER(3), { STATE_SAMPLER(3), sampler_texdim }, WINED3D_GL_EXT_NONE },
5633 { STATE_SAMPLER(4), { STATE_SAMPLER(4), sampler_texdim }, WINED3D_GL_EXT_NONE },
5634 { STATE_SAMPLER(5), { STATE_SAMPLER(5), sampler_texdim }, WINED3D_GL_EXT_NONE },
5635 { STATE_SAMPLER(6), { STATE_SAMPLER(6), sampler_texdim }, WINED3D_GL_EXT_NONE },
5636 { STATE_SAMPLER(7), { STATE_SAMPLER(7), sampler_texdim }, WINED3D_GL_EXT_NONE },
5637 {0 /* Terminate */, { 0, 0 }, WINED3D_GL_EXT_NONE },
5640 /* Context activation and GL locking are done by the caller. */
5641 static void ffp_enable(const struct wined3d_gl_info *gl_info, BOOL enable) {}
5643 static void ffp_fragment_get_caps(const struct wined3d_gl_info *gl_info, struct fragment_caps *caps)
5645 caps->PrimitiveMiscCaps = 0;
5646 caps->TextureOpCaps = WINED3DTEXOPCAPS_ADD
5647 | WINED3DTEXOPCAPS_ADDSIGNED
5648 | WINED3DTEXOPCAPS_ADDSIGNED2X
5649 | WINED3DTEXOPCAPS_MODULATE
5650 | WINED3DTEXOPCAPS_MODULATE2X
5651 | WINED3DTEXOPCAPS_MODULATE4X
5652 | WINED3DTEXOPCAPS_SELECTARG1
5653 | WINED3DTEXOPCAPS_SELECTARG2
5654 | WINED3DTEXOPCAPS_DISABLE;
5656 if (gl_info->supported[ARB_TEXTURE_ENV_COMBINE]
5657 || gl_info->supported[EXT_TEXTURE_ENV_COMBINE]
5658 || gl_info->supported[NV_TEXTURE_ENV_COMBINE4])
5660 caps->TextureOpCaps |= WINED3DTEXOPCAPS_BLENDDIFFUSEALPHA
5661 | WINED3DTEXOPCAPS_BLENDTEXTUREALPHA
5662 | WINED3DTEXOPCAPS_BLENDFACTORALPHA
5663 | WINED3DTEXOPCAPS_BLENDCURRENTALPHA
5664 | WINED3DTEXOPCAPS_LERP
5665 | WINED3DTEXOPCAPS_SUBTRACT;
5667 if (gl_info->supported[ATI_TEXTURE_ENV_COMBINE3]
5668 || gl_info->supported[NV_TEXTURE_ENV_COMBINE4])
5670 caps->TextureOpCaps |= WINED3DTEXOPCAPS_ADDSMOOTH
5671 | WINED3DTEXOPCAPS_MULTIPLYADD
5672 | WINED3DTEXOPCAPS_MODULATEALPHA_ADDCOLOR
5673 | WINED3DTEXOPCAPS_MODULATECOLOR_ADDALPHA
5674 | WINED3DTEXOPCAPS_BLENDTEXTUREALPHAPM;
5676 if (gl_info->supported[ARB_TEXTURE_ENV_DOT3])
5677 caps->TextureOpCaps |= WINED3DTEXOPCAPS_DOTPRODUCT3;
5679 caps->MaxTextureBlendStages = gl_info->limits.textures;
5680 caps->MaxSimultaneousTextures = gl_info->limits.textures;
5683 static void *ffp_fragment_alloc(const struct wined3d_shader_backend_ops *shader_backend, void *shader_priv)
5688 static void ffp_fragment_free(struct wined3d_device *device) {}
5689 static BOOL ffp_color_fixup_supported(struct color_fixup_desc fixup)
5693 TRACE("Checking support for fixup:\n");
5694 dump_color_fixup_desc(fixup);
5697 /* We only support identity conversions. */
5698 if (is_identity_fixup(fixup))
5704 TRACE("[FAILED]\n");
5708 const struct fragment_pipeline ffp_fragment_pipeline = {
5710 ffp_fragment_get_caps,
5713 ffp_color_fixup_supported,
5714 ffp_fragmentstate_template,
5715 FALSE /* we cannot disable projected textures. The vertex pipe has to do it */
5718 static unsigned int num_handlers(const APPLYSTATEFUNC *funcs)
5721 for(i = 0; funcs[i]; i++);
5725 static void multistate_apply_2(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
5727 context->swapchain->device->multistate_funcs[state_id][0](context, state, state_id);
5728 context->swapchain->device->multistate_funcs[state_id][1](context, state, state_id);
5731 static void multistate_apply_3(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id)
5733 context->swapchain->device->multistate_funcs[state_id][0](context, state, state_id);
5734 context->swapchain->device->multistate_funcs[state_id][1](context, state, state_id);
5735 context->swapchain->device->multistate_funcs[state_id][2](context, state, state_id);
5738 static void prune_invalid_states(struct StateEntry *state_table, const struct wined3d_gl_info *gl_info)
5740 unsigned int start, last, i;
5742 start = STATE_TEXTURESTAGE(gl_info->limits.texture_stages, 0);
5743 last = STATE_TEXTURESTAGE(MAX_TEXTURES - 1, WINED3D_HIGHEST_TEXTURE_STATE);
5744 for (i = start; i <= last; ++i)
5746 state_table[i].representative = 0;
5747 state_table[i].apply = state_undefined;
5750 start = STATE_TRANSFORM(WINED3D_TS_TEXTURE0 + gl_info->limits.texture_stages);
5751 last = STATE_TRANSFORM(WINED3D_TS_TEXTURE0 + MAX_TEXTURES - 1);
5752 for (i = start; i <= last; ++i)
5754 state_table[i].representative = 0;
5755 state_table[i].apply = state_undefined;
5758 start = STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(gl_info->limits.blends));
5759 last = STATE_TRANSFORM(WINED3D_TS_WORLD_MATRIX(255));
5760 for (i = start; i <= last; ++i)
5762 state_table[i].representative = 0;
5763 state_table[i].apply = state_undefined;
5767 static void validate_state_table(struct StateEntry *state_table)
5789 static const DWORD simple_states[] =
5795 STATE_VERTEXSHADERCONSTANT,
5796 STATE_PIXELSHADERCONSTANT,
5798 STATE_GEOMETRY_SHADER,
5803 STATE_POINTSPRITECOORDORIGIN,
5804 STATE_BASEVERTEXINDEX,
5807 unsigned int i, current;
5809 for (i = STATE_RENDER(1), current = 0; i <= STATE_RENDER(WINEHIGHEST_RENDER_STATE); ++i)
5811 if (!rs_holes[current].first || i < STATE_RENDER(rs_holes[current].first))
5813 if (!state_table[i].representative)
5814 ERR("State %s (%#x) should have a representative.\n", debug_d3dstate(i), i);
5816 else if (state_table[i].representative)
5817 ERR("State %s (%#x) shouldn't have a representative.\n", debug_d3dstate(i), i);
5819 if (i == STATE_RENDER(rs_holes[current].last)) ++current;
5822 for (i = 0; i < sizeof(simple_states) / sizeof(*simple_states); ++i)
5824 if (!state_table[simple_states[i]].representative)
5825 ERR("State %s (%#x) should have a representative.\n",
5826 debug_d3dstate(simple_states[i]), simple_states[i]);
5829 for (i = 0; i < STATE_HIGHEST + 1; ++i)
5831 DWORD rep = state_table[i].representative;
5834 if (state_table[rep].representative != rep)
5836 ERR("State %s (%#x) has invalid representative %s (%#x).\n",
5837 debug_d3dstate(i), i, debug_d3dstate(rep), rep);
5838 state_table[i].representative = 0;
5843 if (state_table[i].apply)
5844 ERR("State %s (%#x) has both a handler and representative.\n", debug_d3dstate(i), i);
5846 else if (!state_table[i].apply)
5848 ERR("Self representing state %s (%#x) has no handler.\n", debug_d3dstate(i), i);
5854 HRESULT compile_state_table(struct StateEntry *StateTable, APPLYSTATEFUNC **dev_multistate_funcs,
5855 const struct wined3d_gl_info *gl_info, const struct StateEntryTemplate *vertex,
5856 const struct fragment_pipeline *fragment, const struct StateEntryTemplate *misc)
5858 unsigned int i, type, handlers;
5859 APPLYSTATEFUNC multistate_funcs[STATE_HIGHEST + 1][3];
5860 const struct StateEntryTemplate *cur;
5861 BOOL set[STATE_HIGHEST + 1];
5863 memset(multistate_funcs, 0, sizeof(multistate_funcs));
5865 for(i = 0; i < STATE_HIGHEST + 1; i++) {
5866 StateTable[i].representative = 0;
5867 StateTable[i].apply = state_undefined;
5870 for(type = 0; type < 3; type++) {
5871 /* This switch decides the order in which the states are applied */
5873 case 0: cur = misc; break;
5874 case 1: cur = fragment->states; break;
5875 case 2: cur = vertex; break;
5876 default: cur = NULL; /* Stupid compiler */
5880 /* GL extension filtering should not prevent multiple handlers being applied from different
5883 memset(set, 0, sizeof(set));
5885 for(i = 0; cur[i].state; i++) {
5886 APPLYSTATEFUNC *funcs_array;
5888 /* Only use the first matching state with the available extension from one template.
5890 * {D3DRS_FOOBAR, {D3DRS_FOOBAR, func1}, XYZ_FANCY},
5891 * {D3DRS_FOOBAR, {D3DRS_FOOBAR, func2}, 0 }
5893 * if GL_XYZ_fancy is supported, ignore the 2nd line
5895 if(set[cur[i].state]) continue;
5896 /* Skip state lines depending on unsupported extensions */
5897 if (!gl_info->supported[cur[i].extension]) continue;
5898 set[cur[i].state] = TRUE;
5899 /* In some cases having an extension means that nothing has to be
5900 * done for a state, e.g. if GL_ARB_texture_non_power_of_two is
5901 * supported, the texture coordinate fixup can be ignored. If the
5902 * apply function is used, mark the state set(done above) to prevent
5903 * applying later lines, but do not record anything in the state
5906 if (!cur[i].content.representative) continue;
5908 handlers = num_handlers(multistate_funcs[cur[i].state]);
5909 multistate_funcs[cur[i].state][handlers] = cur[i].content.apply;
5912 StateTable[cur[i].state].apply = cur[i].content.apply;
5915 StateTable[cur[i].state].apply = multistate_apply_2;
5916 dev_multistate_funcs[cur[i].state] = HeapAlloc(GetProcessHeap(),
5918 sizeof(**dev_multistate_funcs) * 2);
5919 if (!dev_multistate_funcs[cur[i].state]) {
5923 dev_multistate_funcs[cur[i].state][0] = multistate_funcs[cur[i].state][0];
5924 dev_multistate_funcs[cur[i].state][1] = multistate_funcs[cur[i].state][1];
5927 StateTable[cur[i].state].apply = multistate_apply_3;
5928 funcs_array = HeapReAlloc(GetProcessHeap(),
5930 dev_multistate_funcs[cur[i].state],
5931 sizeof(**dev_multistate_funcs) * 3);
5936 dev_multistate_funcs[cur[i].state] = funcs_array;
5937 dev_multistate_funcs[cur[i].state][2] = multistate_funcs[cur[i].state][2];
5940 ERR("Unexpected amount of state handlers for state %u: %u\n",
5941 cur[i].state, handlers + 1);
5944 if(StateTable[cur[i].state].representative &&
5945 StateTable[cur[i].state].representative != cur[i].content.representative) {
5946 FIXME("State %u has different representatives in different pipeline parts\n",
5949 StateTable[cur[i].state].representative = cur[i].content.representative;
5953 prune_invalid_states(StateTable, gl_info);
5954 validate_state_table(StateTable);
5959 for (i = 0; i <= STATE_HIGHEST; ++i) {
5960 HeapFree(GetProcessHeap(), 0, dev_multistate_funcs[i]);
5963 memset(dev_multistate_funcs, 0, (STATE_HIGHEST + 1)*sizeof(*dev_multistate_funcs));
5965 return E_OUTOFMEMORY;