Module: wine Branch: master Commit: ffc9f535eb7817ea4cd0d0657471e61a9813debd URL: http://source.winehq.org/git/wine.git/?a=commit;h=ffc9f535eb7817ea4cd0d06574...
Author: Henri Verbeet hverbeet@codeweavers.com Date: Fri Jun 14 09:07:12 2013 +0200
wined3d: Handle pre-transformed vertices in the GLSL vertex pipe.
This also avoids a fallback to drawStridedSlow().
---
dlls/wined3d/buffer.c | 11 ++++++----- dlls/wined3d/device.c | 7 ++----- dlls/wined3d/directx.c | 4 ++++ dlls/wined3d/glsl_shader.c | 20 +++++++++++++++----- dlls/wined3d/state.c | 1 + dlls/wined3d/utils.c | 4 ++-- dlls/wined3d/wined3d_private.h | 5 ++++- 7 files changed, 34 insertions(+), 18 deletions(-)
diff --git a/dlls/wined3d/buffer.c b/dlls/wined3d/buffer.c index adfae98..586b16c 100644 --- a/dlls/wined3d/buffer.c +++ b/dlls/wined3d/buffer.c @@ -266,7 +266,7 @@ static BOOL buffer_process_converted_attribute(struct wined3d_buffer *This, }
static BOOL buffer_check_attribute(struct wined3d_buffer *This, const struct wined3d_stream_info *si, - UINT attrib_idx, const BOOL check_d3dcolor, const BOOL is_ffp_position, const BOOL is_ffp_color, + UINT attrib_idx, const BOOL check_d3dcolor, const BOOL check_position, const BOOL is_ffp_color, DWORD *stride_this_run) { const struct wined3d_stream_info_element *attrib = &si->elements[attrib_idx]; @@ -288,7 +288,7 @@ static BOOL buffer_check_attribute(struct wined3d_buffer *This, const struct win
if (!is_ffp_color) FIXME("Test for non-color fixed function WINED3DFMT_B8G8R8A8_UNORM format\n"); } - else if (is_ffp_position && si->position_transformed) + else if (check_position && si->position_transformed) { if (format != WINED3DFMT_R32G32B32A32_FLOAT) { @@ -309,12 +309,13 @@ static BOOL buffer_check_attribute(struct wined3d_buffer *This, const struct win static BOOL buffer_find_decl(struct wined3d_buffer *This) { struct wined3d_device *device = This->resource.device; - const struct wined3d_gl_info *gl_info = &device->adapter->gl_info; + const struct wined3d_adapter *adapter = device->adapter; const struct wined3d_stream_info *si = &device->stream_info; const struct wined3d_state *state = &device->stateBlock->state; + BOOL support_d3dcolor = adapter->gl_info.supported[ARB_VERTEX_ARRAY_BGRA]; + BOOL support_xyzrhw = adapter->d3d_info.xyzrhw; UINT stride_this_run = 0; BOOL ret = FALSE; - BOOL support_d3dcolor = gl_info->supported[ARB_VERTEX_ARRAY_BGRA];
/* In d3d7 the vertex buffer declaration NEVER changes because it is stored in the d3d7 vertex buffer. * Once we have our declaration there is no need to look it up again. Index buffers also never need @@ -386,7 +387,7 @@ static BOOL buffer_find_decl(struct wined3d_buffer *This) */
ret = buffer_check_attribute(This, si, WINED3D_FFP_POSITION, - TRUE, TRUE, FALSE, &stride_this_run) || ret; + TRUE, !support_xyzrhw, FALSE, &stride_this_run) || ret; ret = buffer_check_attribute(This, si, WINED3D_FFP_NORMAL, TRUE, FALSE, FALSE, &stride_this_run) || ret; ret = buffer_check_attribute(This, si, WINED3D_FFP_DIFFUSE, diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 42456b0..464181f 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -332,14 +332,11 @@ void device_update_stream_info(struct wined3d_device *device, const struct wined slow_mask |= -!gl_info->supported[ARB_VERTEX_ARRAY_BGRA] & ((1 << WINED3D_FFP_DIFFUSE) | (1 << WINED3D_FFP_SPECULAR));
- if ((stream_info->position_transformed || (stream_info->use_map & slow_mask)) && !stream_info->all_vbo) - { + if (((stream_info->position_transformed && !device->adapter->d3d_info.xyzrhw) + || (stream_info->use_map & slow_mask)) && !stream_info->all_vbo) device->useDrawStridedSlow = TRUE; - } else - { device->useDrawStridedSlow = FALSE; - } }
if (prev_all_vbo != stream_info->all_vbo) diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index 91e5d1f..067c60b 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -2635,6 +2635,7 @@ static BOOL wined3d_adapter_init_gl_caps(struct wined3d_adapter *adapter) struct wined3d_driver_info *driver_info = &adapter->driver_info; const char *gl_vendor_str, *gl_renderer_str, *gl_version_str; struct wined3d_gl_info *gl_info = &adapter->gl_info; + struct wined3d_vertex_caps vertex_caps; enum wined3d_pci_vendor card_vendor; struct fragment_caps fragment_caps; struct shader_caps shader_caps; @@ -2865,6 +2866,9 @@ static BOOL wined3d_adapter_init_gl_caps(struct wined3d_adapter *adapter) adapter->d3d_info.limits.vs_uniform_count = shader_caps.vs_uniform_count; adapter->d3d_info.limits.ps_uniform_count = shader_caps.ps_uniform_count;
+ adapter->vertex_pipe->vp_get_caps(gl_info, &vertex_caps); + adapter->d3d_info.xyzrhw = vertex_caps.xyzrhw; + adapter->fragment_pipe->get_caps(gl_info, &fragment_caps); adapter->d3d_info.limits.ffp_blend_stages = fragment_caps.MaxTextureBlendStages; adapter->d3d_info.limits.ffp_textures = fragment_caps.MaxSimultaneousTextures; diff --git a/dlls/wined3d/glsl_shader.c b/dlls/wined3d/glsl_shader.c index 412c601..e14d7ab 100644 --- a/dlls/wined3d/glsl_shader.c +++ b/dlls/wined3d/glsl_shader.c @@ -5011,11 +5011,20 @@ static GLhandleARB shader_glsl_generate_ffp_vertex_shader(struct wined3d_shader_ shader_addline(buffer, "float m;\n"); shader_addline(buffer, "vec3 r;\n");
- shader_addline(buffer, "vec4 ec_pos = gl_ModelViewMatrix * gl_Vertex;\n"); - shader_addline(buffer, "gl_Position = gl_ProjectionMatrix * ec_pos;\n"); - if (settings->clipping) - shader_addline(buffer, "gl_ClipVertex = ec_pos;\n"); - shader_addline(buffer, "ec_pos /= ec_pos.w;\n"); + if (settings->transformed) + { + shader_addline(buffer, "vec4 ec_pos = vec4(gl_Vertex.xyz, 1.0);\n"); + shader_addline(buffer, "gl_Position = gl_ProjectionMatrix * ec_pos;\n"); + shader_addline(buffer, "if (gl_Vertex.w != 0.0) gl_Position /= gl_Vertex.w;\n"); + } + else + { + shader_addline(buffer, "vec4 ec_pos = gl_ModelViewMatrix * gl_Vertex;\n"); + shader_addline(buffer, "gl_Position = gl_ProjectionMatrix * ec_pos;\n"); + if (settings->clipping) + shader_addline(buffer, "gl_ClipVertex = ec_pos;\n"); + shader_addline(buffer, "ec_pos /= ec_pos.w;\n"); + }
if (!settings->normal) shader_addline(buffer, "vec3 normal = vec3(0.0);\n"); @@ -6737,6 +6746,7 @@ static void glsl_vertex_pipe_vp_enable(const struct wined3d_gl_info *gl_info, BO
static void glsl_vertex_pipe_vp_get_caps(const struct wined3d_gl_info *gl_info, struct wined3d_vertex_caps *caps) { + caps->xyzrhw = TRUE; caps->max_active_lights = gl_info->limits.lights; caps->max_vertex_blend_matrices = 0; caps->max_vertex_blend_matrix_index = 0; diff --git a/dlls/wined3d/state.c b/dlls/wined3d/state.c index 74261ec..ffce803 100644 --- a/dlls/wined3d/state.c +++ b/dlls/wined3d/state.c @@ -5641,6 +5641,7 @@ static void ffp_free(struct wined3d_device *device) {}
static void vp_ffp_get_caps(const struct wined3d_gl_info *gl_info, struct wined3d_vertex_caps *caps) { + caps->xyzrhw = FALSE; caps->max_active_lights = gl_info->limits.lights; caps->max_vertex_blend_matrices = gl_info->limits.blends; caps->max_vertex_blend_matrix_index = 0; diff --git a/dlls/wined3d/utils.c b/dlls/wined3d/utils.c index b83a05a..5b7fb3c 100644 --- a/dlls/wined3d/utils.c +++ b/dlls/wined3d/utils.c @@ -3552,8 +3552,7 @@ void wined3d_ffp_get_vs_settings(const struct wined3d_state *state, const struct { memset(settings, 0, sizeof(*settings));
- settings->clipping = state->render_states[WINED3D_RS_CLIPPING] - && state->render_states[WINED3D_RS_CLIPPLANEENABLE]; + settings->transformed = 1; settings->point_size = state->gl_primitive_type == GL_POINTS; if (!state->render_states[WINED3D_RS_FOGENABLE]) settings->fog_mode = WINED3D_FFP_VS_FOG_OFF; @@ -3573,6 +3572,7 @@ void wined3d_ffp_get_vs_settings(const struct wined3d_state *state, const struct return; }
+ settings->transformed = 0; settings->clipping = state->render_states[WINED3D_RS_CLIPPING] && state->render_states[WINED3D_RS_CLIPPLANEENABLE]; settings->normal = !!(si->use_map & (1 << WINED3D_FFP_NORMAL)); diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index 82a4584..1fbe081 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -1193,6 +1193,7 @@ struct fragment_pipeline
struct wined3d_vertex_caps { + BOOL xyzrhw; DWORD max_active_lights; DWORD max_vertex_blend_matrices; DWORD max_vertex_blend_matrix_index; @@ -1606,6 +1607,7 @@ struct wined3d_d3d_limits struct wined3d_d3d_info { struct wined3d_d3d_limits limits; + BOOL xyzrhw; BOOL vs_clipping; DWORD valid_rt_mask; }; @@ -1723,6 +1725,7 @@ struct wined3d_ffp_vs_settings DWORD ambient_source : 2; DWORD specular_source : 2;
+ DWORD transformed : 1; DWORD clipping : 1; DWORD normal : 1; DWORD normalize : 1; @@ -1731,7 +1734,7 @@ struct wined3d_ffp_vs_settings DWORD point_size : 1; DWORD fog_mode : 2; DWORD texcoords : 8; /* MAX_TEXTURES */ - DWORD padding : 16; + DWORD padding : 15;
BYTE texgen[MAX_TEXTURES]; };