/*===========================================================================*/ /* */ /* Mesa-3.0 DirectX 6 Driver Build 5 */ /* */ /* By Leigh McRae */ /* */ /* http://www.altsoftware.com/ */ /* */ /* Copyright (c) 1999-1998 alt.software inc. All Rights Reserved */ /*===========================================================================*/ #include "D3DHAL.h" /*===========================================================================*/ /* Macros. */ /*===========================================================================*/ #define SRCBLEND_MAP(gl,d3d,fall) if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwSrcBlendCaps & d3d ) \ { \ sprintf( buffer, "SRC Blend: %s -> %s", # gl, # d3d ); \ DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), buffer )); \ pShared->dwSrcBlendCaps[index] = d3d; \ } \ else \ { \ sprintf( buffer, "SRC Blend: %s -> %s", # gl, # fall ); \ DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), buffer )); \ pShared->dwSrcBlendCaps[index] = fall; \ } #define DSTBLEND_MAP(gl,d3d,fall) if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwDestBlendCaps & d3d ) \ { \ sprintf( buffer, "DST Blend: %s -> %s", # gl, # d3d ); \ DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), buffer )); \ pShared->dwDestBlendCaps[index] = d3d; \ } \ else \ { \ sprintf( buffer, "DST Blend: %s -> %s", # gl, # fall ); \ DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), buffer )); \ pShared->dwDestBlendCaps[index] = fall; \ } /*===========================================================================*/ /* I use this function to handle the fact that the D3D texture blending and */ /* OpenGL texture blending functions don't map one to one. Also there is the*/ /* problem with cards not supporting all the D3D functions. So I use the CAPS*/ /* of the card to make a table of functions that will have defaults for the */ /* unsupported functions. */ /* So first I fill the table with the fallback function then I check to see */ /* if the card supports the requested function. If it does I replace the */ /* default thats already in the array. Now order does matter as I used an */ /* enum type in D3DShared.h so that the mapping would be a little easier. */ /*===========================================================================*/ /* RETURN: */ /*===========================================================================*/ void AlphaBlendTableHAL( PMESAD3DHAL pHAL ) { PMESAD3DSHARED pShared = &pHAL->shared; int index; char buffer[128]; DPF(( DBG_FUNC, "AlphaBlendTableHAL();" )); /* Make the fallback for the Source blend. */ for( index = 0; index < 14; index++ ) { switch( index ) { case s_zero: SRCBLEND_MAP( GL_ZERO, D3DBLEND_ZERO, D3DBLEND_ONE ); break; case s_one: SRCBLEND_MAP( GL_ONE, D3DBLEND_ONE, D3DBLEND_ONE ); break; case s_dst_color: SRCBLEND_MAP( GL_DST_COLOR, D3DBLEND_DESTCOLOR, D3DBLEND_ONE ); break; case s_one_minus_dst_color: SRCBLEND_MAP( GL_ONE_MINUS_DST_COLOR, D3DBLEND_INVDESTCOLOR, D3DBLEND_ONE ); break; case s_src_alpha: SRCBLEND_MAP( GL_SRC_ALPHA, D3DBLEND_SRCALPHA, D3DBLEND_ONE ); break; case s_one_minus_src_alpha: SRCBLEND_MAP( GL_ONE_MINUS_SRC_ALPHA, D3DBLEND_INVSRCALPHA, D3DBLEND_ONE ); break; case s_dst_alpha: SRCBLEND_MAP( GL_DST_ALPHA, D3DBLEND_DESTALPHA, D3DBLEND_ONE ); break; case s_one_minus_dst_alpha: SRCBLEND_MAP( GL_ONE_MINUS_DST_ALPHA, D3DBLEND_INVDESTALPHA, D3DBLEND_ONE ); break; case s_src_alpha_saturate: SRCBLEND_MAP( GL_SRC_ALPHA_SATURATE, D3DBLEND_SRCALPHASAT, D3DBLEND_ONE ); break; case s_constant_color: SRCBLEND_MAP( GL_CONSTANT_COLOR, D3DBLEND_SRCCOLOR, D3DBLEND_ONE ); break; case s_one_minus_constant_color: SRCBLEND_MAP( GL_ONE_MINUS_CONSTANT_COLOR, D3DBLEND_INVSRCCOLOR, D3DBLEND_ONE ); break; case s_constant_alpha: SRCBLEND_MAP( GL_CONSTANT_ALPHA, D3DBLEND_BOTHSRCALPHA, D3DBLEND_ONE ); break; case s_one_minus_constant_alpha: SRCBLEND_MAP( GL_ONE_MINUS_CONSTANT_ALPHA, D3DBLEND_BOTHINVSRCALPHA, D3DBLEND_ONE ); break; } } /* Make the fallback for the Destination blend. */ for( index = 0; index < 14; index++ ) { switch( index ) { case d_zero: DSTBLEND_MAP( GL_ZERO, D3DBLEND_ZERO, D3DBLEND_ONE ); break; case d_one: DSTBLEND_MAP( GL_ONE, D3DBLEND_ONE, D3DBLEND_ONE ); break; case d_src_color: DSTBLEND_MAP( GL_SRC_COLOR, D3DBLEND_SRCCOLOR, D3DBLEND_ONE ); break; case d_one_minus_src_color: DSTBLEND_MAP( GL_ONE_MINUS_SRC_COLOR, D3DBLEND_INVSRCCOLOR, D3DBLEND_ONE ); break; case d_src_alpha: DSTBLEND_MAP( GL_SRC_ALPHA, D3DBLEND_SRCALPHA, D3DBLEND_ONE ); break; case d_one_minus_src_alpha: DSTBLEND_MAP( GL_ONE_MINUS_SRC_ALPHA, D3DBLEND_INVSRCALPHA, D3DBLEND_ONE ); break; case d_dst_alpha: DSTBLEND_MAP( GL_DST_ALPHA, D3DBLEND_DESTALPHA, D3DBLEND_ONE ); break; case d_one_minus_dst_alpha: DSTBLEND_MAP( GL_ONE_MINUS_DST_ALPHA, D3DBLEND_INVDESTALPHA, D3DBLEND_ONE ); break; case d_constant_color: DSTBLEND_MAP( GL_CONSTANT_COLOR, D3DBLEND_DESTCOLOR, D3DBLEND_ONE ); break; case d_one_minus_constant_color: DSTBLEND_MAP( GL_ONE_MINUS_CONSTANT_COLOR, D3DBLEND_INVDESTCOLOR, D3DBLEND_ONE ); break; case d_constant_alpha: DSTBLEND_MAP( GL_CONSTANT_ALPHAR, D3DBLEND_BOTHSRCALPHA, D3DBLEND_ONE ); break; case d_one_minus_constant_alpha: DSTBLEND_MAP( GL_ONE_MINUS_CONSTANT_ALPHA, D3DBLEND_BOTHINVSRCALPHA, D3DBLEND_ONE ); break; } } /* Make the fallbacks for the texture functions. */ for( index = 0; index < 4; index++ ) { switch( index ) { case d3dtblend_decal: if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_DECAL ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_DECAL -> D3DTBLEND_DECAL" )); pShared->dwTexFunc[index] = D3DTBLEND_DECAL; } else { if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_MODULATE ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_DECAL -> D3DTBLEND_MODULATE" )); pShared->dwTexFunc[index] = D3DTBLEND_MODULATE; } else { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_DECAL -> D3DTBLEND_ADD" )); pShared->dwTexFunc[index] = D3DTBLEND_ADD; } } break; case d3dtblend_decalalpha: if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_DECALALPHA ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_DECALALPHA -> D3DTBLEND_DECALALPHA" )); pShared->dwTexFunc[index] = D3DTBLEND_DECALALPHA; } else { if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_DECAL ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_DECALALPA -> D3DTBLEND_DECAL" )); pShared->dwTexFunc[index] = D3DTBLEND_DECAL; } else { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_DECALALPHA -> D3DTBLEND_ADD" )); pShared->dwTexFunc[index] = D3DTBLEND_ADD; } } break; case d3dtblend_modulate: if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_MODULATE ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATE -> D3DTBLEND_MODULATE" )); pShared->dwTexFunc[index] = D3DTBLEND_MODULATE; } else { if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_MODULATEALPHA ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATE -> D3DTBLEND_MODULATEALPHA" )); pShared->dwTexFunc[index] = D3DTBLEND_MODULATEALPHA; } else if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_DECAL ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATE -> D3DTBLEND_DECAL" )); pShared->dwTexFunc[index] = D3DTBLEND_DECAL; } else { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATE -> D3DTBLEND_ADD" )); pShared->dwTexFunc[index] = D3DTBLEND_ADD; } } break; case d3dtblend_modulatealpha: if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_MODULATEALPHA ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATEALPHA -> D3DTBLEND_MODULATEALPHA" )); pShared->dwTexFunc[index] = D3DTBLEND_MODULATEALPHA; } else { if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_MODULATE ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATEALPHA -> D3DTBLEND_MODULATE" )); pShared->dwTexFunc[index] = D3DTBLEND_MODULATE; } else if ( pHAL->D3DHWDevDesc.dpcTriCaps.dwTextureBlendCaps & D3DTBLEND_DECAL ) { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATEALPHA -> D3DTBLEND_DECALE" )); pShared->dwTexFunc[index] = D3DTBLEND_DECAL; } else { DPF(( (DBG_CNTX_INFO|DBG_TXT_INFO), "D3DTBLEND_MODULATEALPHA -> D3DTBLEND_ADD" )); pShared->dwTexFunc[index] = D3DTBLEND_ADD; } } break; } } }