/* * R_EnableBumpmap * * Enables bumpmapping while updating program parameters to reflect the * specified material. */ void R_EnableBumpmap(r_material_t *material, boolean_t enable) { if (!r_state.lighting_enabled) return; if (!r_bumpmap->value) return; R_UseMaterial(material); if (r_state.bumpmap_enabled == enable) return; r_state.bumpmap_enabled = enable; if (enable) { // toggle state R_EnableAttribute("TANGENT"); R_ProgramParameter1i("BUMPMAP", 1); } else { R_DisableAttribute("TANGENT"); R_ProgramParameter1i("BUMPMAP", 0); } }
/** * @brief */ void R_UseMaterial_default(const r_material_t *material) { r_default_program_t *p = &r_default_program; if (!material || !material->normalmap || !r_bumpmap->value || r_draw_bsp_lightmaps->value) { R_DisableAttribute(R_ARRAY_TANGENT); R_ProgramParameter1i(&p->normalmap, 0); return; } R_EnableAttribute(R_ARRAY_TANGENT); R_BindNormalmapTexture(material->normalmap->texnum); R_ProgramParameter1i(&p->normalmap, 1); if (material->specularmap) { R_BindSpecularmapTexture(material->specularmap->texnum); R_ProgramParameter1i(&p->glossmap, 1); } else { R_ProgramParameter1i(&p->glossmap, 0); } R_ProgramParameter1f(&p->bump, material->cm->bump * r_bumpmap->value); R_ProgramParameter1f(&p->parallax, material->cm->parallax * r_parallax->value); R_ProgramParameter1f(&p->hardness, material->cm->hardness * r_hardness->value); R_ProgramParameter1f(&p->specular, material->cm->specular * r_specular->value); }
/** * @brief Enable or disable realtime dynamic lighting for models * @param lights The lights to enable * @param numLights The amount of lights in the given lights list * @param inShadow Whether model is shadowed from the sun * @param enable Whether to turn realtime lighting on or off */ void R_EnableModelLights (const light_t **lights, int numLights, bool inShadow, bool enable) { int i; int maxLights = r_dynamic_lights->integer; vec4_t blackColor = {0.0, 0.0, 0.0, 1.0}; const vec4_t whiteColor = {1.0, 1.0, 1.0, 1.0}; const vec4_t defaultLight0Position = {0.0, 0.0, 1.0, 0.0}; vec3_t lightPositions[MAX_GL_LIGHTS]; vec4_t lightParams[MAX_GL_LIGHTS]; if (r_programs->integer == 0) { /* Fixed function path renderer got only the sunlight */ /* Setup OpenGL light #0 to act as a sun and environment light */ glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_COLOR_MATERIAL); #ifndef GL_VERSION_ES_CM_1_0 glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE); #endif glLightf(GL_LIGHT0, GL_CONSTANT_ATTENUATION, 1.0); glLightf(GL_LIGHT0, GL_LINEAR_ATTENUATION, 0); glLightf(GL_LIGHT0, GL_QUADRATIC_ATTENUATION, 0); glLightfv(GL_LIGHT0, GL_SPECULAR, blackColor); glLightfv(GL_LIGHT0, GL_AMBIENT, refdef.modelAmbientColor); glLightfv(GL_LIGHT0, GL_POSITION, refdef.sunVector); if (enable) { if (inShadow) { /* ambient only */ glLightfv(GL_LIGHT0, GL_DIFFUSE, blackColor); } else { /* Full sunlight */ glLightfv(GL_LIGHT0, GL_DIFFUSE, refdef.sunDiffuseColor); } } else { /* restore the default OpenGL state */ glDisable(GL_LIGHTING); glDisable(GL_COLOR_MATERIAL); glLightfv(GL_LIGHT0, GL_POSITION, defaultLight0Position); glLightfv(GL_LIGHT0, GL_AMBIENT, blackColor); glLightfv(GL_LIGHT0, GL_DIFFUSE, whiteColor); glLightfv(GL_LIGHT0, GL_SPECULAR, whiteColor); } return; } assert(numLights <= MAX_GL_LIGHTS); if (!enable || !r_state.lighting_enabled) { if (r_state.dynamic_lighting_enabled) { R_DisableAttribute("TANGENTS"); /** @todo is it a good idea? */ if (maxLights) { for (i = 0; i < maxLights; i++) Vector4Set(lightParams[i], 0, 0, 0, 1); /* Send light data to shaders */ R_ProgramParameter3fvs("LIGHTPOSITIONS", maxLights, (GLfloat *)lightPositions); R_ProgramParameter4fvs("LIGHTPARAMS", maxLights, (GLfloat *)lightParams); } } r_state.dynamic_lighting_enabled = false; return; } /** @todo assert? */ if (numLights > maxLights) numLights = maxLights; r_state.dynamic_lighting_enabled = true; R_EnableAttribute("TANGENTS"); R_UseMaterial(&defaultMaterial); R_ProgramParameter3fv("AMBIENT", refdef.modelAmbientColor); if (inShadow) { R_ProgramParameter3fv("SUNCOLOR", blackColor); } else { R_ProgramParameter3fv("SUNCOLOR", refdef.sunDiffuseColor); } if (!maxLights) return; for (i = 0; i < numLights; i++) { const light_t *light = lights[i]; GLPositionTransform(r_locals.world_matrix, light->origin, lightPositions[i]); VectorCopy(light->color, lightParams[i]); lightParams[i][3] = 16.0 / (light->radius * light->radius); } /* if there aren't enough active lights, turn off the rest */ for (; i < maxLights; i++) Vector4Set(lightParams[i], 0, 0, 0, 1); /* Send light data to shaders */ R_ProgramParameter3fvs("LIGHTPOSITIONS", maxLights, (GLfloat *)lightPositions); R_ProgramParameter4fvs("LIGHTPARAMS", maxLights, (GLfloat *)lightParams); }