summaryrefslogtreecommitdiff
path: root/src/mesa/drivers/dri/radeon/radeon_state.c
diff options
context:
space:
mode:
authorRoland Scheidegger <rscheidegger@gmx.ch>2005-10-17 00:54:12 +0000
committerRoland Scheidegger <rscheidegger@gmx.ch>2005-10-17 00:54:12 +0000
commit2d61d301171620efe624d83a5457f4094eb49cba (patch)
treefc53f97e4e2cba24bdf654fc2aba72975c18ccaf /src/mesa/drivers/dri/radeon/radeon_state.c
parentdd5a86339f8b10f72c8a0e15c14463af3e0f717d (diff)
add GL_EXT_fog_coord support to radeon driver. No vtxfmt code (just uses fallback) yet. May cause a tcl fallback if fog coord is used together with separate specular lighting. Fog factors are precomputed and then submitted instead of the raw coords (chip limitation, same as on r200).
Diffstat (limited to 'src/mesa/drivers/dri/radeon/radeon_state.c')
-rw-r--r--src/mesa/drivers/dri/radeon/radeon_state.c77
1 files changed, 37 insertions, 40 deletions
diff --git a/src/mesa/drivers/dri/radeon/radeon_state.c b/src/mesa/drivers/dri/radeon/radeon_state.c
index 28033881c5..681de914e8 100644
--- a/src/mesa/drivers/dri/radeon/radeon_state.c
+++ b/src/mesa/drivers/dri/radeon/radeon_state.c
@@ -55,6 +55,8 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#include "radeon_vtxfmt.h"
#include "drirenderbuffer.h"
+static void radeonUpdateSpecular( GLcontext *ctx );
+
/* =============================================================
* Alpha blending
*/
@@ -329,9 +331,6 @@ static void radeonFogfv( GLcontext *ctx, GLenum pname, const GLfloat *param )
union { int i; float f; } c, d;
GLchan col[4];
- c.i = rmesa->hw.fog.cmd[FOG_C];
- d.i = rmesa->hw.fog.cmd[FOG_D];
-
switch (pname) {
case GL_FOG_MODE:
if (!ctx->Fog.Enabled)
@@ -341,30 +340,24 @@ static void radeonFogfv( GLcontext *ctx, GLenum pname, const GLfloat *param )
switch (ctx->Fog.Mode) {
case GL_LINEAR:
rmesa->hw.tcl.cmd[TCL_UCP_VERT_BLEND_CTL] |= RADEON_TCL_FOG_LINEAR;
- if (ctx->Fog.Start == ctx->Fog.End) {
- c.f = 1.0F;
- d.f = 1.0F;
- }
- else {
- c.f = ctx->Fog.End/(ctx->Fog.End-ctx->Fog.Start);
- d.f = 1.0/(ctx->Fog.End-ctx->Fog.Start);
- }
break;
case GL_EXP:
rmesa->hw.tcl.cmd[TCL_UCP_VERT_BLEND_CTL] |= RADEON_TCL_FOG_EXP;
- c.f = 0.0;
- d.f = ctx->Fog.Density;
break;
case GL_EXP2:
rmesa->hw.tcl.cmd[TCL_UCP_VERT_BLEND_CTL] |= RADEON_TCL_FOG_EXP2;
- c.f = 0.0;
- d.f = -(ctx->Fog.Density * ctx->Fog.Density);
break;
default:
return;
}
- break;
+ /* fallthrough */
case GL_FOG_DENSITY:
+ case GL_FOG_START:
+ case GL_FOG_END:
+ if (!ctx->Fog.Enabled)
+ return;
+ c.i = rmesa->hw.fog.cmd[FOG_C];
+ d.i = rmesa->hw.fog.cmd[FOG_D];
switch (ctx->Fog.Mode) {
case GL_EXP:
c.f = 0.0;
@@ -374,13 +367,7 @@ static void radeonFogfv( GLcontext *ctx, GLenum pname, const GLfloat *param )
c.f = 0.0;
d.f = -(ctx->Fog.Density * ctx->Fog.Density);
break;
- default:
- break;
- }
- break;
- case GL_FOG_START:
- case GL_FOG_END:
- if (ctx->Fog.Mode == GL_LINEAR) {
+ case GL_LINEAR:
if (ctx->Fog.Start == ctx->Fog.End) {
c.f = 1.0F;
d.f = 1.0F;
@@ -388,27 +375,29 @@ static void radeonFogfv( GLcontext *ctx, GLenum pname, const GLfloat *param )
c.f = ctx->Fog.End/(ctx->Fog.End-ctx->Fog.Start);
d.f = 1.0/(ctx->Fog.End-ctx->Fog.Start);
}
+ break;
+ default:
+ break;
+ }
+ if (c.i != rmesa->hw.fog.cmd[FOG_C] || d.i != rmesa->hw.fog.cmd[FOG_D]) {
+ RADEON_STATECHANGE( rmesa, fog );
+ rmesa->hw.fog.cmd[FOG_C] = c.i;
+ rmesa->hw.fog.cmd[FOG_D] = d.i;
}
break;
case GL_FOG_COLOR:
RADEON_STATECHANGE( rmesa, ctx );
UNCLAMPED_FLOAT_TO_RGB_CHAN( col, ctx->Fog.Color );
- rmesa->hw.ctx.cmd[CTX_PP_FOG_COLOR] =
+ rmesa->hw.ctx.cmd[CTX_PP_FOG_COLOR] &= ~RADEON_FOG_COLOR_MASK;
+ rmesa->hw.ctx.cmd[CTX_PP_FOG_COLOR] |=
radeonPackColor( 4, col[0], col[1], col[2], 0 );
break;
- case GL_FOG_COORDINATE_SOURCE_EXT:
- /* What to do?
- */
+ case GL_FOG_COORD_SRC:
+ radeonUpdateSpecular( ctx );
break;
default:
return;
}
-
- if (c.i != rmesa->hw.fog.cmd[FOG_C] || d.i != rmesa->hw.fog.cmd[FOG_D]) {
- RADEON_STATECHANGE( rmesa, fog );
- rmesa->hw.fog.cmd[FOG_C] = c.i;
- rmesa->hw.fog.cmd[FOG_D] = d.i;
- }
}
@@ -692,6 +681,7 @@ static void radeonUpdateSpecular( GLcontext *ctx )
{
radeonContextPtr rmesa = RADEON_CONTEXT(ctx);
u_int32_t p = rmesa->hw.ctx.cmd[CTX_PP_CNTL];
+ GLuint flag = 0;
RADEON_STATECHANGE( rmesa, tcl );
@@ -730,13 +720,22 @@ static void radeonUpdateSpecular( GLcontext *ctx )
}
if (ctx->Fog.Enabled) {
- rmesa->hw.tcl.cmd[TCL_OUTPUT_VTXSEL] |= RADEON_TCL_COMPUTE_SPECULAR;
rmesa->hw.tcl.cmd[TCL_OUTPUT_VTXFMT] |= RADEON_TCL_VTX_PK_SPEC;
-
- /* Bizzare: have to leave lighting enabled to get fog.
- */
- rmesa->hw.tcl.cmd[TCL_LIGHT_MODEL_CTL] |= RADEON_LIGHTING_ENABLE;
+ if (ctx->Fog.FogCoordinateSource == GL_FRAGMENT_DEPTH) {
+ rmesa->hw.tcl.cmd[TCL_OUTPUT_VTXSEL] |= RADEON_TCL_COMPUTE_SPECULAR;
+ /* Bizzare: have to leave lighting enabled to get fog. */
+ rmesa->hw.tcl.cmd[TCL_LIGHT_MODEL_CTL] |= RADEON_LIGHTING_ENABLE;
+ }
+ else {
+ /* cannot do tcl fog factor calculation with fog coord source
+ * (send precomputed factors). Cannot use precomputed fog
+ * factors together with tcl spec light (need tcl fallback) */
+ flag = (rmesa->hw.tcl.cmd[TCL_OUTPUT_VTXSEL] &
+ RADEON_TCL_COMPUTE_SPECULAR) != 0;
+ }
}
+
+ TCL_FALLBACK( ctx, RADEON_TCL_FALLBACK_FOGCOORDSPEC, flag);
if (NEED_SECONDARY_COLOR(ctx)) {
assert( (p & RADEON_SPECULAR_ENABLE) != 0 );
@@ -1809,8 +1808,6 @@ static void radeonEnable( GLcontext *ctx, GLenum cap, GLboolean state )
rmesa->hw.tcl.cmd[TCL_UCP_VERT_BLEND_CTL] &= ~RADEON_TCL_FOG_MASK;
}
radeonUpdateSpecular( ctx ); /* for PK_SPEC */
- if (rmesa->TclFallback)
- radeonChooseVertexState( ctx );
_mesa_allow_light_in_model( ctx, !state );
break;