From: Elizabeth Figura zfigura@codeweavers.com
Preparation for storing just this structure in the push constant buffer. --- dlls/wined3d/cs.c | 3 +- dlls/wined3d/device.c | 10 +++---- dlls/wined3d/glsl_shader.c | 39 ++++++++++++------------ dlls/wined3d/stateblock.c | 55 +++++++++++++++++++++------------- dlls/wined3d/wined3d_private.h | 13 ++++++-- 5 files changed, 71 insertions(+), 49 deletions(-)
diff --git a/dlls/wined3d/cs.c b/dlls/wined3d/cs.c index 275941dd183..c5e9d3edcb5 100644 --- a/dlls/wined3d/cs.c +++ b/dlls/wined3d/cs.c @@ -2065,8 +2065,7 @@ static void wined3d_cs_exec_set_light(struct wined3d_cs *cs, const void *data) }
light_info->OriginalParms = op->light.OriginalParms; - light_info->position = op->light.position; - light_info->direction = op->light.direction; + light_info->constants = op->light.constants; }
void wined3d_device_context_emit_set_light(struct wined3d_device_context *context, diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index e445679ec2f..a2ca7ddc848 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -2999,7 +2999,7 @@ static void init_transformed_lights(struct lights_settings *ls, continue;
light = &ls->lights[index]; - wined3d_vec4_transform(&vec4, &light_info->direction, &state->transforms[WINED3D_TS_VIEW]); + wined3d_vec4_transform(&vec4, &light_info->constants.direction, &state->transforms[WINED3D_TS_VIEW]); light->direction = *(struct wined3d_vec3 *)&vec4; wined3d_vec3_normalise(&light->direction);
@@ -3017,7 +3017,7 @@ static void init_transformed_lights(struct lights_settings *ls,
light = &ls->lights[index];
- wined3d_vec4_transform(&light->position, &light_info->position, &state->transforms[WINED3D_TS_VIEW]); + wined3d_vec4_transform(&light->position, &light_info->constants.position, &state->transforms[WINED3D_TS_VIEW]); light->range = light_info->OriginalParms.range; light->c_att = light_info->OriginalParms.attenuation0; light->l_att = light_info->OriginalParms.attenuation1; @@ -3037,8 +3037,8 @@ static void init_transformed_lights(struct lights_settings *ls,
light = &ls->lights[index];
- wined3d_vec4_transform(&light->position, &light_info->position, &state->transforms[WINED3D_TS_VIEW]); - wined3d_vec4_transform(&vec4, &light_info->direction, &state->transforms[WINED3D_TS_VIEW]); + wined3d_vec4_transform(&light->position, &light_info->constants.position, &state->transforms[WINED3D_TS_VIEW]); + wined3d_vec4_transform(&vec4, &light_info->constants.direction, &state->transforms[WINED3D_TS_VIEW]); light->direction = *(struct wined3d_vec3 *)&vec4; wined3d_vec3_normalise(&light->direction); light->range = light_info->OriginalParms.range; @@ -3063,7 +3063,7 @@ static void init_transformed_lights(struct lights_settings *ls,
light = &ls->lights[index];
- wined3d_vec4_transform(&vec4, &light_info->position, &state->transforms[WINED3D_TS_VIEW]); + wined3d_vec4_transform(&vec4, &light_info->constants.position, &state->transforms[WINED3D_TS_VIEW]); *(struct wined3d_vec3 *)&light->position = *(struct wined3d_vec3 *)&vec4; wined3d_vec3_normalise((struct wined3d_vec3 *)&light->position); light->diffuse = light_info->OriginalParms.diffuse; diff --git a/dlls/wined3d/glsl_shader.c b/dlls/wined3d/glsl_shader.c index c0d75897857..67fb41d862a 100644 --- a/dlls/wined3d/glsl_shader.c +++ b/dlls/wined3d/glsl_shader.c @@ -1539,48 +1539,49 @@ static void shader_glsl_ffp_vertex_light_uniform(const struct wined3d_context_gl const struct wined3d_state *state, unsigned int light, const struct wined3d_light_info *light_info, struct glsl_shader_prog_link *prog) { + const struct wined3d_light_constants *constants = &light_info->constants; const struct wined3d_matrix *view = &state->transforms[WINED3D_TS_VIEW]; const struct wined3d_gl_info *gl_info = context_gl->gl_info; struct wined3d_vec4 vec4;
- GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].diffuse, 1, &light_info->OriginalParms.diffuse.r)); - GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].specular, 1, &light_info->OriginalParms.specular.r)); - GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].ambient, 1, &light_info->OriginalParms.ambient.r)); + GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].diffuse, 1, &constants->diffuse.r)); + GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].specular, 1, &constants->specular.r)); + GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].ambient, 1, &constants->ambient.r));
switch (light_info->OriginalParms.type) { case WINED3D_LIGHT_POINT: - wined3d_vec4_transform(&vec4, &light_info->position, view); + wined3d_vec4_transform(&vec4, &constants->position, view); GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].position, 1, &vec4.x)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].range, light_info->OriginalParms.range)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].c_att, light_info->OriginalParms.attenuation0)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].l_att, light_info->OriginalParms.attenuation1)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].q_att, light_info->OriginalParms.attenuation2)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].range, constants->range)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].c_att, constants->const_att)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].l_att, constants->linear_att)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].q_att, constants->quad_att)); break;
case WINED3D_LIGHT_SPOT: - wined3d_vec4_transform(&vec4, &light_info->position, view); + wined3d_vec4_transform(&vec4, &constants->position, view); GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].position, 1, &vec4.x));
- wined3d_vec4_transform(&vec4, &light_info->direction, view); + wined3d_vec4_transform(&vec4, &constants->direction, view); GL_EXTCALL(glUniform3fv(prog->vs.light_location[light].direction, 1, &vec4.x));
- GL_EXTCALL(glUniform1f(prog->vs.light_location[light].range, light_info->OriginalParms.range)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].falloff, light_info->OriginalParms.falloff)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].c_att, light_info->OriginalParms.attenuation0)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].l_att, light_info->OriginalParms.attenuation1)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].q_att, light_info->OriginalParms.attenuation2)); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].cos_htheta, cosf(light_info->OriginalParms.theta / 2.0f))); - GL_EXTCALL(glUniform1f(prog->vs.light_location[light].cos_hphi, cosf(light_info->OriginalParms.phi / 2.0f))); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].range, constants->range)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].falloff, constants->falloff)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].c_att, constants->const_att)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].l_att, constants->linear_att)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].q_att, constants->quad_att)); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].cos_htheta, cosf(constants->theta / 2.0f))); + GL_EXTCALL(glUniform1f(prog->vs.light_location[light].cos_hphi, cosf(constants->phi / 2.0f))); break;
case WINED3D_LIGHT_DIRECTIONAL: - wined3d_vec4_transform(&vec4, &light_info->direction, view); + wined3d_vec4_transform(&vec4, &constants->direction, view); GL_EXTCALL(glUniform3fv(prog->vs.light_location[light].direction, 1, &vec4.x)); break;
case WINED3D_LIGHT_PARALLELPOINT: - wined3d_vec4_transform(&vec4, &light_info->position, view); + wined3d_vec4_transform(&vec4, &constants->position, view); GL_EXTCALL(glUniform4fv(prog->vs.light_location[light].position, 1, &vec4.x)); break;
diff --git a/dlls/wined3d/stateblock.c b/dlls/wined3d/stateblock.c index 548bf9aa477..f92ab4b4961 100644 --- a/dlls/wined3d/stateblock.c +++ b/dlls/wined3d/stateblock.c @@ -661,6 +661,7 @@ static void set_light_changed(struct wined3d_stateblock *stateblock, struct wine static HRESULT wined3d_light_state_set_light(struct wined3d_light_state *state, unsigned int light_idx, const struct wined3d_light *params, struct wined3d_light_info **light_info) { + struct wined3d_light_constants *constants; struct wined3d_light_info *object;
if (!(object = wined3d_light_state_get_light(state, light_idx))) @@ -677,6 +678,8 @@ static HRESULT wined3d_light_state_set_light(struct wined3d_light_state *state, rb_put(&state->lights_tree, (void *)(ULONG_PTR)light_idx, &object->entry); }
+ constants = &object->constants; + object->OriginalParms = *params;
/* Initialize the object. */ @@ -689,46 +692,58 @@ static HRESULT wined3d_light_state_set_light(struct wined3d_light_state *state, params->direction.x, params->direction.y, params->direction.z, params->range, params->falloff, params->theta, params->phi);
+ constants->diffuse = params->diffuse; + constants->specular = params->specular; + constants->ambient = params->ambient; + + constants->range = params->range; + constants->falloff = params->falloff; + constants->const_att = params->attenuation0; + constants->linear_att = params->attenuation1; + constants->quad_att = params->attenuation2; + constants->theta = params->theta; + constants->phi = params->phi; + switch (params->type) { case WINED3D_LIGHT_POINT: /* Position */ - object->position.x = params->position.x; - object->position.y = params->position.y; - object->position.z = params->position.z; - object->position.w = 1.0f; + constants->position.x = params->position.x; + constants->position.y = params->position.y; + constants->position.z = params->position.z; + constants->position.w = 1.0f; /* FIXME: Range */ break;
case WINED3D_LIGHT_DIRECTIONAL: /* Direction */ - object->direction.x = -params->direction.x; - object->direction.y = -params->direction.y; - object->direction.z = -params->direction.z; - object->direction.w = 0.0f; + constants->direction.x = -params->direction.x; + constants->direction.y = -params->direction.y; + constants->direction.z = -params->direction.z; + constants->direction.w = 0.0f; break;
case WINED3D_LIGHT_SPOT: /* Position */ - object->position.x = params->position.x; - object->position.y = params->position.y; - object->position.z = params->position.z; - object->position.w = 1.0f; + constants->position.x = params->position.x; + constants->position.y = params->position.y; + constants->position.z = params->position.z; + constants->position.w = 1.0f;
/* Direction */ - object->direction.x = params->direction.x; - object->direction.y = params->direction.y; - object->direction.z = params->direction.z; - object->direction.w = 0.0f; + constants->direction.x = params->direction.x; + constants->direction.y = params->direction.y; + constants->direction.z = params->direction.z; + constants->direction.w = 0.0f;
/* FIXME: Range */ break;
case WINED3D_LIGHT_PARALLELPOINT: - object->position.x = params->position.x; - object->position.y = params->position.y; - object->position.z = params->position.z; - object->position.w = 1.0f; + constants->position.x = params->position.x; + constants->position.y = params->position.y; + constants->position.z = params->position.z; + constants->position.w = 1.0f; break;
default: diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index 9ad1d0f8ba5..9580406ce3a 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -2064,6 +2064,14 @@ void context_state_drawbuf(struct wined3d_context *context, void context_state_fb(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id);
+struct wined3d_light_constants +{ + struct wined3d_color diffuse, specular, ambient; + struct wined3d_vec4 position, direction; + float range, falloff, theta, phi; + float const_att, linear_att, quad_att; +}; + /***************************************************************************** * Internal representation of a light */ @@ -2074,9 +2082,8 @@ struct wined3d_light_info LONG glIndex; BOOL enabled;
- /* Converted parms to speed up swapping lights */ - struct wined3d_vec4 position; - struct wined3d_vec4 direction; + /* Computed constants used by the vertex pipe. */ + struct wined3d_light_constants constants;
struct rb_entry entry; struct list changed_entry;