Show textureunit.cpp syntax highlighted
/***************************************************************************
textureunit.cpp - Texture unit management
-------------------
begin : Sun Mar 30 2003
copyright : (C) 2003 by Reality Rift Studios
email : mattias@realityrift.com
***************************************************************************
The contents of this file are subject to the Mozilla Public License Version
1.1 (the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.mozilla.org/MPL/
Software distributed under the License is distributed on an "AS IS" basis,
WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
for the specific language governing rights and limitations under the
License.
The Original Code is the NeoEngine, NeoDevOpenGL, textureunit.cpp
The Initial Developer of the Original Code is Mattias Jansson.
Portions created by Mattias Jansson are Copyright (C) 2003
Reality Rift Studios. All Rights Reserved.
***************************************************************************/
#include "textureunit.h"
#include <neoengine/material.h>
using namespace NeoEngine;
namespace NeoOGL
{
unsigned int TextureUnit::s_uiCurUnit = 0;
TextureUnit::TextureUnit( Device *pkDevice, unsigned int uiID ) :
m_pkDevice( pkDevice ),
m_uiID( uiID ),
m_pkTexture( 0 ),
m_uiUV( 0 ),
m_bGotTransform( false ),
m_eTexGen( TextureLayer::NOGEN )
{
m_akTarget[0].m_eTarget = GL_TEXTURE_1D;
m_akTarget[1].m_eTarget = GL_TEXTURE_2D;
m_akTarget[2].m_eTarget = GL_TEXTURE_3D;
m_akTarget[3].m_eTarget = GL_TEXTURE_CUBE_MAP_ARB;
m_akTarget[0].m_pkTexture = 0;
m_akTarget[1].m_pkTexture = 0;
m_akTarget[2].m_pkTexture = 0;
m_akTarget[3].m_pkTexture = 0;
m_akTarget[0].m_bEnabled = false;
m_akTarget[1].m_bEnabled = false;
m_akTarget[2].m_bEnabled = false;
m_akTarget[3].m_bEnabled = false;
glDisable( GL_TEXTURE_1D );
glDisable( GL_TEXTURE_2D );
//glDisable( GL_TEXTURE_3D ); We don't support 3D textures anyway
if( m_pkDevice->m_kExtensions.IsSupported( Extensions::ARB_TEXTURE_CUBE_MAP ) )
glDisable( GL_TEXTURE_CUBE_MAP_ARB );
}
TextureUnit::~TextureUnit()
{
}
bool TextureUnit::SetBlendMode( unsigned int uiSrcMode, unsigned int uiDstMode, float fFactor )
{
//We don't want to be called on primary texture unit
assert( m_uiID );
SetActiveTextureUnit( m_uiID );
switch( uiSrcMode )
{
case BlendMode::SRC_ONE:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = 1 * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = 1 * RGBs + 1 * RGBd
if( m_pkDevice->m_kExtensions.IsSupported( Extensions::ARB_TEXENV_ADD ) )
{
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_ADD );
return true;
}
else
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = 1 * RGBs + RGBs * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = 1 * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = 1 * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = 1 * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = 1 * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = 1 * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ZERO:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = 0 * RGBs + 0 * RGBd
return false;
}
case BlendMode::DEST_ONE:
{
// RGBf = 0 * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = 0 * RGBs + RGBs * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = 0 * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = 0 * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = 0 * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = 0 * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = 0 * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_DESTCOLOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = RGBd * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = RGBd * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = RGBd * RGBs + RGBs * RGBd = ( RGBs * RGBd ) << 1
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = RGBd * RGBs + ( 1 - RGBs ) * RGBd = RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = RGBd * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = RGBd * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = RGBd * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = RGBd * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ONEMINUSDESTCOLOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = ( 1 - RGBd ) * RGBs + 0 * RGBd
return false;
}
case BlendMode::DEST_ONE:
{
// RGBf = ( 1 - RGBd ) * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = ( 1 - RGBd ) * RGBs + RGBs * RGBd = RGBs
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = ( 1 - RGBd ) * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_SRCCOLOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = RGBs * RGBs + 0 * RGBd
return false;
}
case BlendMode::DEST_ONE:
{
// RGBf = RGBs * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = RGBs * RGBs + RGBs * RGBd = RGBs * ( 1 + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = RGBs * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = RGBs * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = RGBs * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = RGBs * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = RGBs * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_FACTOR:
{
assert( false );
break;
}
case BlendMode::SRC_SRCALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = As * RGBs + 0 * RGBd
return false;
}
case BlendMode::DEST_ONE:
{
// RGBf = As * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = As * RGBs + RGBs * RGBd = RGBs * ( As + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = As * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = As * RGBs + As * RGBd = As * ( RGBs + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = As * RGBs + ( 1 - As ) * RGBd
// Af = As + Ad
// This allows two layers with srcalpha|oneminussrcalpha to be rendered
// correctly, since the final framebuffer blend of srcalpha|oneminussrcalpha
// should not use only base layer texture alpha, since that would also mask out
// parts of second layer
//FIXME: What about alpha?
//glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL );
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = As * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = As * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ONEMINUSSRCALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = ( 1 - As ) * RGBs + 0 * RGBd
return false;
}
case BlendMode::DEST_ONE:
{
// RGBf = ( 1 - As ) * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = ( 1 - As ) * RGBs + RGBs * RGBd = RGBs * ( ( 1 - As ) + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = ( 1 - As ) * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = ( 1 - As ) * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = ( 1 - As ) * RGBs + ( 1 - As ) * RGBd = ( 1 - As ) * ( RGBs + RGBd )
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = ( 1 - As ) * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = ( 1 - As ) * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_DESTALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = Ad * RGBs + 0 * RGBd
return false;
}
case BlendMode::DEST_ONE:
{
// RGBf = Ad * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = Ad * RGBs + RGBs * RGBd = RGBs * ( Ad + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = Ad * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = Ad * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = Ad * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = Ad * RGBs + Ad * RGBd = Ad * ( RGBs + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = Ad * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ONEMINUSDESTALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = ( 1 - Ad ) * RGBs + 0 * RGBd
return false;
}
case BlendMode::DEST_ONE:
{
// RGBf = ( 1 - Ad ) * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = ( 1 - Ad ) * RGBs + RGBs * RGBd = RGBs * ( ( 1 - Ad ) + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = ( 1 - Ad ) * RGBs + ( 1 - RGBs ) * RGBd
return false;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + Ad * RGBd = Ad * ( RGBs + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + ( 1 - Ad ) * RGBd = ( 1 - Ad ) * ( RGBs + RGBd )
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ALPHASATURATE:
{
return false;
}
default:
{
assert( false );
return false;
}
}
return true;
}
bool TextureUnitCombine::SetBlendMode( unsigned int uiSrcMode, unsigned int uiDstMode, float fFactor )
{
//We don't want to be called on primary texture unit
assert( m_uiID );
SetActiveTextureUnit( m_uiID );
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB );
glTexEnvf( GL_TEXTURE_ENV, GL_RGB_SCALE_ARB, 1.0f );
glTexEnvf( GL_TEXTURE_ENV, GL_ALPHA_SCALE, 1.0f );
switch( uiSrcMode )
{
case BlendMode::SRC_LERPCOLOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_LERPCOLOR:
{
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PRIMARY_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_COLOR );
return true;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_LERPALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_LERPALPHA:
{
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PRIMARY_COLOR_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_ALPHA );
return true;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ONE:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = 1 * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = 1 * RGBs + 1 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_ADD );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_ADD );
return true;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = 1 * RGBs + RGBs * RGBd
//FIXME: Allow usage of multiple TMUs (i.e return new "next" TMU instead of bool)
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = 1 * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvfv( GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, (GLfloat*)&Color::WHITE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_CONSTANT_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = 1 * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = 1 * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = 1 * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = 1 * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ZERO:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = 0 * RGBs + 0 * RGBd
glTexEnvfv( GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, (GLfloat*)&Color::BLACK );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_CONSTANT_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_CONSTANT_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = 0 * RGBs + 1 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = 0 * RGBs + RGBs * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = 0 * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = 0 * RGBs + As * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = 0 * RGBs + ( 1 - As ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = 0 * RGBs + Ad * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = 0 * RGBs + ( 1 - Ad ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_DESTCOLOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = RGBd * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = RGBd * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = RGBd * RGBs + RGBs * RGBd = ( RGBs * RGBd ) << 1
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
glTexEnvf( GL_TEXTURE_ENV, GL_RGB_SCALE_ARB, 2.0f );
glTexEnvf( GL_TEXTURE_ENV, GL_ALPHA_SCALE, 2.0f );
return true;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = RGBd * RGBs + ( 1 - RGBs ) * RGBd = RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = RGBd * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = RGBd * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = RGBd * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = RGBd * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ONEMINUSDESTCOLOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = ( 1 - RGBd ) * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = ( 1 - RGBd ) * RGBs + 1 * RGBd
glTexEnvfv( GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, (GLfloat*)&Color::WHITE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_CONSTANT_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = ( 1 - RGBd ) * RGBs + RGBs * RGBd = RGBs
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = ( 1 - RGBd ) * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + As * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + ( 1 - As ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + Ad * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = ( 1 - RGBd ) * RGBs + ( 1 - Ad ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_SRCCOLOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = RGBs * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_MODULATE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = RGBs * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = RGBs * RGBs + RGBs * RGBd = RGBs * ( 1 + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = RGBs * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = RGBs * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = RGBs * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = RGBs * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = RGBs * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_FACTOR:
{
switch( uiDstMode )
{
case BlendMode::DEST_ONEMINUSFACTOR:
{
float afColor[4] = { fFactor, fFactor, fFactor, fFactor };
glTexEnvfv( GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, afColor );
// RGBf = As * RGBs + ( 1 - As ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_CONSTANT_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
default:
{
assert( false );
break;
}
}
return false;
}
case BlendMode::SRC_SRCALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = As * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = As * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = As * RGBs + RGBs * RGBd = RGBs * ( As + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = As * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = As * RGBs + As * RGBd = As * ( RGBs + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = As * RGBs + ( 1 - As ) * RGBd
// Af = As + Ad
// This allows two layers with srcalpha|oneminussrcalpha to be rendered
// correctly, since the final framebuffer blend of srcalpha|oneminussrcalpha
// should not use only base layer texture alpha, since that would also mask out
// parts of second layer
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_ADD );
return true;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = As * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = As * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ONEMINUSSRCALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = ( 1 - As ) * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = ( 1 - As ) * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = ( 1 - As ) * RGBs + RGBs * RGBd = RGBs * ( ( 1 - As ) + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = ( 1 - As ) * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = ( 1 - As ) * RGBs + As * RGBd
// This allows two layers with oneminussrcalpha|srcalpha to be rendered
// correctly, since the final framebuffer blend of srcalpha|oneminussrcalpha
// should not use only base layer texture alpha, since that would also mask out
// parts of second layer
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_ADD );
return true;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = ( 1 - As ) * RGBs + ( 1 - As ) * RGBd = ( 1 - As ) * ( RGBs + RGBd )
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = ( 1 - As ) * RGBs + Ad * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = ( 1 - As ) * RGBs + ( 1 - Ad ) * RGBd
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_DESTALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = Ad * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = Ad * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = Ad * RGBs + RGBs * RGBd = RGBs * ( Ad + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = Ad * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = Ad * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = Ad * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = Ad * RGBs + Ad * RGBd = Ad * ( RGBs + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = Ad * RGBs + ( 1 - Ad ) * RGBd
// See note about about alpha add
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_ADD );
return true;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ONEMINUSDESTALPHA:
{
switch( uiDstMode )
{
case BlendMode::DEST_ZERO:
{
// RGBf = ( 1 - Ad ) * RGBs + 0 * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_ONE:
{
// RGBf = ( 1 - Ad ) * RGBs + 1 * RGBd
return false;
}
case BlendMode::DEST_SRCCOLOR:
{
//RGBf = ( 1 - Ad ) * RGBs + RGBs * RGBd = RGBs * ( ( 1 - Ad ) + RGBd )
return false;
}
case BlendMode::DEST_ONEMINUSSRCCOLOR:
{
// RGBf = ( 1 - Ad ) * RGBs + ( 1 - RGBs ) * RGBd
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_REPLACE );
return true;
}
case BlendMode::DEST_SRCALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + As * RGBd
return false;
}
case BlendMode::DEST_ONEMINUSSRCALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + ( 1 - As ) * RGBd
return false;
}
case BlendMode::DEST_DESTALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + Ad * RGBd
// See note about about alpha add
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_ONE_MINUS_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_ARB, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_ARB, GL_PREVIOUS_ARB );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_ARB, GL_SRC_ALPHA );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_ARB, GL_ADD );
}
case BlendMode::DEST_ONEMINUSDESTALPHA:
{
// RGBf = ( 1 - Ad ) * RGBs + ( 1 - Ad ) * RGBd = ( 1 - Ad ) * ( RGBs + RGBd )
return false;
}
default:
assert( false );
}
return false;
}
case BlendMode::SRC_ALPHASATURATE:
{
return false;
}
default:
{
assert( false );
return false;
}
}
return true;
}
}; // namespace NeoOGL
See more files for this project here