Fix GL_MIN and GL_MAX blend equations (set blend factors accordingly). Fix errors when blending is disabled (set blend equation and function to default values).
This commit is contained in:
parent
d359f96a18
commit
b9cbd52724
|
@ -69,37 +69,24 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|||
#define R200_COMB_FCN_MAX (5 << 12)
|
||||
#define R200_COMB_FCN_RSUB_CLAMP (6 << 12)
|
||||
#define R200_COMB_FCN_RSUB_NOCLAMP (7 << 12)
|
||||
#define R200_SRC_BLEND_GL_ZERO (32 << 16)
|
||||
#define R200_SRC_BLEND_GL_ONE (33 << 16)
|
||||
#define R200_SRC_BLEND_GL_SRC_COLOR (34 << 16)
|
||||
#define R200_SRC_BLEND_GL_ONE_MINUS_SRC_COLOR (35 << 16)
|
||||
#define R200_SRC_BLEND_GL_DST_COLOR (36 << 16)
|
||||
#define R200_SRC_BLEND_GL_ONE_MINUS_DST_COLOR (37 << 16)
|
||||
#define R200_SRC_BLEND_GL_SRC_ALPHA (38 << 16)
|
||||
#define R200_SRC_BLEND_GL_ONE_MINUS_SRC_ALPHA (39 << 16)
|
||||
#define R200_SRC_BLEND_GL_DST_ALPHA (40 << 16)
|
||||
#define R200_SRC_BLEND_GL_ONE_MINUS_DST_ALPHA (41 << 16)
|
||||
#define R200_SRC_BLEND_GL_SRC_ALPHA_SATURATE (42 << 16)
|
||||
#define R200_SRC_BLEND_GL_CONST_COLOR (43 << 16)
|
||||
#define R200_SRC_BLEND_GL_ONE_MINUS_CONST_COLOR (44 << 16)
|
||||
#define R200_SRC_BLEND_GL_CONST_ALPHA (45 << 16)
|
||||
#define R200_SRC_BLEND_GL_ONE_MINUS_CONST_ALPHA (46 << 16)
|
||||
#define R200_SRC_BLEND_MASK (63 << 16)
|
||||
#define R200_DST_BLEND_GL_ZERO (32 << 24)
|
||||
#define R200_DST_BLEND_GL_ONE (33 << 24)
|
||||
#define R200_DST_BLEND_GL_SRC_COLOR (34 << 24)
|
||||
#define R200_DST_BLEND_GL_ONE_MINUS_SRC_COLOR (35 << 24)
|
||||
#define R200_DST_BLEND_GL_DST_COLOR (36 << 24)
|
||||
#define R200_DST_BLEND_GL_ONE_MINUS_DST_COLOR (37 << 24)
|
||||
#define R200_DST_BLEND_GL_SRC_ALPHA (38 << 24)
|
||||
#define R200_DST_BLEND_GL_ONE_MINUS_SRC_ALPHA (39 << 24)
|
||||
#define R200_DST_BLEND_GL_DST_ALPHA (40 << 24)
|
||||
#define R200_DST_BLEND_GL_ONE_MINUS_DST_ALPHA (41 << 24)
|
||||
#define R200_DST_BLEND_GL_CONST_COLOR (43 << 24)
|
||||
#define R200_DST_BLEND_GL_ONE_MINUS_CONST_COLOR (44 << 24)
|
||||
#define R200_DST_BLEND_GL_CONST_ALPHA (45 << 24)
|
||||
#define R200_DST_BLEND_GL_ONE_MINUS_CONST_ALPHA (46 << 24)
|
||||
#define R200_DST_BLEND_MASK (63 << 24)
|
||||
#define R200_BLEND_GL_ZERO (32)
|
||||
#define R200_BLEND_GL_ONE (33)
|
||||
#define R200_BLEND_GL_SRC_COLOR (34)
|
||||
#define R200_BLEND_GL_ONE_MINUS_SRC_COLOR (35)
|
||||
#define R200_BLEND_GL_DST_COLOR (36)
|
||||
#define R200_BLEND_GL_ONE_MINUS_DST_COLOR (37)
|
||||
#define R200_BLEND_GL_SRC_ALPHA (38)
|
||||
#define R200_BLEND_GL_ONE_MINUS_SRC_ALPHA (39)
|
||||
#define R200_BLEND_GL_DST_ALPHA (40)
|
||||
#define R200_BLEND_GL_ONE_MINUS_DST_ALPHA (41)
|
||||
#define R200_BLEND_GL_SRC_ALPHA_SATURATE (42) /* src factor only */
|
||||
#define R200_BLEND_GL_CONST_COLOR (43)
|
||||
#define R200_BLEND_GL_ONE_MINUS_CONST_COLOR (44)
|
||||
#define R200_BLEND_GL_CONST_ALPHA (45)
|
||||
#define R200_BLEND_GL_ONE_MINUS_CONST_ALPHA (46)
|
||||
#define R200_BLEND_MASK (63)
|
||||
#define R200_SRC_BLEND_SHIFT (16)
|
||||
#define R200_DST_BLEND_SHIFT (24)
|
||||
#define R200_RB3D_DEPTHOFFSET 0x1c24
|
||||
#define R200_RB3D_DEPTHPITCH 0x1c28
|
||||
#define R200_DEPTHPITCH_MASK 0x00001ff8
|
||||
|
|
|
@ -104,156 +104,160 @@ static void r200AlphaFunc( GLcontext *ctx, GLenum func, GLfloat ref )
|
|||
rmesa->hw.ctx.cmd[CTX_PP_MISC] = pp_misc;
|
||||
}
|
||||
|
||||
static void r200BlendEquationSeparate( GLcontext *ctx,
|
||||
GLenum modeRGB, GLenum modeA )
|
||||
/**
|
||||
* Calculate the hardware blend factor setting. This same function is used
|
||||
* for source and destination of both alpha and RGB.
|
||||
*
|
||||
* \returns
|
||||
* The hardware register value for the specified blend factor. This value
|
||||
* will need to be shifted into the correct position for either source or
|
||||
* destination factor.
|
||||
*
|
||||
* \todo
|
||||
* Since the two cases where source and destination are handled differently
|
||||
* are essentially error cases, they should never happen. Determine if these
|
||||
* cases can be removed.
|
||||
*/
|
||||
static int blend_factor( GLenum factor, GLboolean is_src )
|
||||
{
|
||||
int func;
|
||||
|
||||
switch ( factor ) {
|
||||
case GL_ZERO:
|
||||
func = R200_BLEND_GL_ZERO;
|
||||
break;
|
||||
case GL_ONE:
|
||||
func = R200_BLEND_GL_ONE;
|
||||
break;
|
||||
case GL_DST_COLOR:
|
||||
func = R200_BLEND_GL_DST_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_DST_COLOR:
|
||||
func = R200_BLEND_GL_ONE_MINUS_DST_COLOR;
|
||||
break;
|
||||
case GL_SRC_COLOR:
|
||||
func = R200_BLEND_GL_SRC_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_SRC_COLOR:
|
||||
func = R200_BLEND_GL_ONE_MINUS_SRC_COLOR;
|
||||
break;
|
||||
case GL_SRC_ALPHA:
|
||||
func = R200_BLEND_GL_SRC_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_SRC_ALPHA:
|
||||
func = R200_BLEND_GL_ONE_MINUS_SRC_ALPHA;
|
||||
break;
|
||||
case GL_DST_ALPHA:
|
||||
func = R200_BLEND_GL_DST_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_DST_ALPHA:
|
||||
func = R200_BLEND_GL_ONE_MINUS_DST_ALPHA;
|
||||
break;
|
||||
case GL_SRC_ALPHA_SATURATE:
|
||||
func = (is_src) ? R200_BLEND_GL_SRC_ALPHA_SATURATE : R200_BLEND_GL_ZERO;
|
||||
break;
|
||||
case GL_CONSTANT_COLOR:
|
||||
func = R200_BLEND_GL_CONST_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_CONSTANT_COLOR:
|
||||
func = R200_BLEND_GL_ONE_MINUS_CONST_COLOR;
|
||||
break;
|
||||
case GL_CONSTANT_ALPHA:
|
||||
func = R200_BLEND_GL_CONST_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_CONSTANT_ALPHA:
|
||||
func = R200_BLEND_GL_ONE_MINUS_CONST_ALPHA;
|
||||
break;
|
||||
default:
|
||||
func = (is_src) ? R200_BLEND_GL_ONE : R200_BLEND_GL_ZERO;
|
||||
}
|
||||
return func;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets both the blend equation and the blend function.
|
||||
* This is done in a single
|
||||
* function because some blend equations (i.e., \c GL_MIN and \c GL_MAX)
|
||||
* change the interpretation of the blend function.
|
||||
* Also, make sure that blend function and blend equation are set to their default
|
||||
* value if color blending is not enabled, since at least blend equations GL_MIN
|
||||
* and GL_FUNC_REVERSE_SUBTRACT will cause wrong results otherwise for
|
||||
* unknown reasons.
|
||||
*/
|
||||
static void r200_set_blend_state( GLcontext * ctx )
|
||||
{
|
||||
r200ContextPtr rmesa = R200_CONTEXT(ctx);
|
||||
GLuint b = rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] & ~R200_COMB_FCN_MASK;
|
||||
GLuint cntl = rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] &
|
||||
~(R200_ROP_ENABLE | R200_ALPHA_BLEND_ENABLE);
|
||||
|
||||
assert( modeRGB == modeA );
|
||||
int func = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
|
||||
(R200_BLEND_GL_ZERO << R200_DST_BLEND_SHIFT);
|
||||
int eqn = R200_COMB_FCN_ADD_CLAMP;
|
||||
|
||||
switch ( modeRGB ) {
|
||||
R200_STATECHANGE( rmesa, ctx );
|
||||
|
||||
if (ctx->Color._LogicOpEnabled) {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] = cntl | R200_ROP_ENABLE;
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = eqn | func;
|
||||
return;
|
||||
} else if (ctx->Color.BlendEnabled) {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] = cntl | R200_ALPHA_BLEND_ENABLE;
|
||||
}
|
||||
else {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] = cntl;
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = eqn | func;
|
||||
return;
|
||||
}
|
||||
|
||||
func = (blend_factor( ctx->Color.BlendSrcRGB, GL_TRUE ) << R200_SRC_BLEND_SHIFT) |
|
||||
(blend_factor( ctx->Color.BlendDstRGB, GL_FALSE ) << R200_DST_BLEND_SHIFT);
|
||||
|
||||
switch(ctx->Color.BlendEquationRGB) {
|
||||
case GL_FUNC_ADD:
|
||||
case GL_LOGIC_OP:
|
||||
b |= R200_COMB_FCN_ADD_CLAMP;
|
||||
eqn = R200_COMB_FCN_ADD_CLAMP;
|
||||
break;
|
||||
|
||||
case GL_FUNC_SUBTRACT:
|
||||
b |= R200_COMB_FCN_SUB_CLAMP;
|
||||
eqn = R200_COMB_FCN_SUB_CLAMP;
|
||||
break;
|
||||
|
||||
case GL_FUNC_REVERSE_SUBTRACT:
|
||||
b |= R200_COMB_FCN_RSUB_CLAMP;
|
||||
eqn = R200_COMB_FCN_RSUB_CLAMP;
|
||||
break;
|
||||
|
||||
case GL_MIN:
|
||||
b |= R200_COMB_FCN_MIN;
|
||||
eqn = R200_COMB_FCN_MIN;
|
||||
func = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
|
||||
(R200_BLEND_GL_ONE << R200_DST_BLEND_SHIFT);
|
||||
break;
|
||||
|
||||
case GL_MAX:
|
||||
b |= R200_COMB_FCN_MAX;
|
||||
eqn = R200_COMB_FCN_MAX;
|
||||
func = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
|
||||
(R200_BLEND_GL_ONE << R200_DST_BLEND_SHIFT);
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
fprintf( stderr, "[%s:%u] Invalid RGB blend equation (0x%04x).\n",
|
||||
__func__, __LINE__, ctx->Color.BlendEquationRGB );
|
||||
return;
|
||||
}
|
||||
|
||||
R200_STATECHANGE( rmesa, ctx );
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = b;
|
||||
if ( ctx->Color._LogicOpEnabled ) {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] |= R200_ROP_ENABLE;
|
||||
} else {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] &= ~R200_ROP_ENABLE;
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = eqn | func;
|
||||
}
|
||||
|
||||
static void r200BlendEquationSeparate( GLcontext *ctx,
|
||||
GLenum modeRGB, GLenum modeA )
|
||||
{
|
||||
r200_set_blend_state( ctx );
|
||||
}
|
||||
|
||||
static void r200BlendFuncSeparate( GLcontext *ctx,
|
||||
GLenum sfactorRGB, GLenum dfactorRGB,
|
||||
GLenum sfactorA, GLenum dfactorA )
|
||||
{
|
||||
r200ContextPtr rmesa = R200_CONTEXT(ctx);
|
||||
GLuint b = rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] &
|
||||
~(R200_SRC_BLEND_MASK | R200_DST_BLEND_MASK);
|
||||
|
||||
switch ( ctx->Color.BlendSrcRGB ) {
|
||||
case GL_ZERO:
|
||||
b |= R200_SRC_BLEND_GL_ZERO;
|
||||
break;
|
||||
case GL_ONE:
|
||||
b |= R200_SRC_BLEND_GL_ONE;
|
||||
break;
|
||||
case GL_DST_COLOR:
|
||||
b |= R200_SRC_BLEND_GL_DST_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_DST_COLOR:
|
||||
b |= R200_SRC_BLEND_GL_ONE_MINUS_DST_COLOR;
|
||||
break;
|
||||
case GL_SRC_COLOR:
|
||||
b |= R200_SRC_BLEND_GL_SRC_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_SRC_COLOR:
|
||||
b |= R200_SRC_BLEND_GL_ONE_MINUS_SRC_COLOR;
|
||||
break;
|
||||
case GL_SRC_ALPHA:
|
||||
b |= R200_SRC_BLEND_GL_SRC_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_SRC_ALPHA:
|
||||
b |= R200_SRC_BLEND_GL_ONE_MINUS_SRC_ALPHA;
|
||||
break;
|
||||
case GL_DST_ALPHA:
|
||||
b |= R200_SRC_BLEND_GL_DST_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_DST_ALPHA:
|
||||
b |= R200_SRC_BLEND_GL_ONE_MINUS_DST_ALPHA;
|
||||
break;
|
||||
case GL_SRC_ALPHA_SATURATE:
|
||||
b |= R200_SRC_BLEND_GL_SRC_ALPHA_SATURATE;
|
||||
break;
|
||||
case GL_CONSTANT_COLOR:
|
||||
b |= R200_SRC_BLEND_GL_CONST_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_CONSTANT_COLOR:
|
||||
b |= R200_SRC_BLEND_GL_ONE_MINUS_CONST_COLOR;
|
||||
break;
|
||||
case GL_CONSTANT_ALPHA:
|
||||
b |= R200_SRC_BLEND_GL_CONST_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_CONSTANT_ALPHA:
|
||||
b |= R200_SRC_BLEND_GL_ONE_MINUS_CONST_ALPHA;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
switch ( ctx->Color.BlendDstRGB ) {
|
||||
case GL_ZERO:
|
||||
b |= R200_DST_BLEND_GL_ZERO;
|
||||
break;
|
||||
case GL_ONE:
|
||||
b |= R200_DST_BLEND_GL_ONE;
|
||||
break;
|
||||
case GL_SRC_COLOR:
|
||||
b |= R200_DST_BLEND_GL_SRC_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_SRC_COLOR:
|
||||
b |= R200_DST_BLEND_GL_ONE_MINUS_SRC_COLOR;
|
||||
break;
|
||||
case GL_SRC_ALPHA:
|
||||
b |= R200_DST_BLEND_GL_SRC_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_SRC_ALPHA:
|
||||
b |= R200_DST_BLEND_GL_ONE_MINUS_SRC_ALPHA;
|
||||
break;
|
||||
case GL_DST_COLOR:
|
||||
b |= R200_DST_BLEND_GL_DST_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_DST_COLOR:
|
||||
b |= R200_DST_BLEND_GL_ONE_MINUS_DST_COLOR;
|
||||
break;
|
||||
case GL_DST_ALPHA:
|
||||
b |= R200_DST_BLEND_GL_DST_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_DST_ALPHA:
|
||||
b |= R200_DST_BLEND_GL_ONE_MINUS_DST_ALPHA;
|
||||
break;
|
||||
case GL_CONSTANT_COLOR:
|
||||
b |= R200_DST_BLEND_GL_CONST_COLOR;
|
||||
break;
|
||||
case GL_ONE_MINUS_CONSTANT_COLOR:
|
||||
b |= R200_DST_BLEND_GL_ONE_MINUS_CONST_COLOR;
|
||||
break;
|
||||
case GL_CONSTANT_ALPHA:
|
||||
b |= R200_DST_BLEND_GL_CONST_ALPHA;
|
||||
break;
|
||||
case GL_ONE_MINUS_CONSTANT_ALPHA:
|
||||
b |= R200_DST_BLEND_GL_ONE_MINUS_CONST_ALPHA;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
R200_STATECHANGE( rmesa, ctx );
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = b;
|
||||
r200_set_blend_state( ctx );
|
||||
}
|
||||
|
||||
|
||||
|
@ -1738,17 +1742,8 @@ static void r200Enable( GLcontext *ctx, GLenum cap, GLboolean state )
|
|||
break;
|
||||
|
||||
case GL_BLEND:
|
||||
R200_STATECHANGE( rmesa, ctx );
|
||||
if (state) {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] |= R200_ALPHA_BLEND_ENABLE;
|
||||
} else {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] &= ~R200_ALPHA_BLEND_ENABLE;
|
||||
}
|
||||
if ( ctx->Color._LogicOpEnabled ) {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] |= R200_ROP_ENABLE;
|
||||
} else {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] &= ~R200_ROP_ENABLE;
|
||||
}
|
||||
case GL_COLOR_LOGIC_OP:
|
||||
r200_set_blend_state( ctx );
|
||||
break;
|
||||
|
||||
case GL_CLIP_PLANE0:
|
||||
|
@ -1864,15 +1859,6 @@ static void r200Enable( GLcontext *ctx, GLenum cap, GLboolean state )
|
|||
}
|
||||
break;
|
||||
|
||||
case GL_COLOR_LOGIC_OP:
|
||||
R200_STATECHANGE( rmesa, ctx );
|
||||
if ( ctx->Color._LogicOpEnabled ) {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] |= R200_ROP_ENABLE;
|
||||
} else {
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] &= ~R200_ROP_ENABLE;
|
||||
}
|
||||
break;
|
||||
|
||||
case GL_NORMALIZE:
|
||||
R200_STATECHANGE( rmesa, tcl );
|
||||
if ( state ) {
|
||||
|
|
|
@ -367,8 +367,8 @@ void r200InitState( r200ContextPtr rmesa )
|
|||
rmesa->hw.ctx.cmd[CTX_RE_SOLID_COLOR] = 0x00000000;
|
||||
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = (R200_COMB_FCN_ADD_CLAMP |
|
||||
R200_SRC_BLEND_GL_ONE |
|
||||
R200_DST_BLEND_GL_ZERO );
|
||||
(R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
|
||||
(R200_BLEND_GL_ZERO << R200_DST_BLEND_SHIFT));
|
||||
|
||||
rmesa->hw.ctx.cmd[CTX_RB3D_DEPTHOFFSET] =
|
||||
rmesa->r200Screen->depthOffset + rmesa->r200Screen->fbLocation;
|
||||
|
|
Loading…
Reference in New Issue