add 2-pass support for models
This commit is contained in:
+52
-19
@@ -244,8 +244,6 @@ bool Model::LoadMilkshapeAscii( CString sPath )
|
|||||||
THROW
|
THROW
|
||||||
strcpy( Material.szName, szName );
|
strcpy( Material.szName, szName );
|
||||||
|
|
||||||
Material.bSphereMapped = ((CString)Material.szName).Find("sphere") != -1;
|
|
||||||
|
|
||||||
// ambient
|
// ambient
|
||||||
if( f.GetLine( sLine ) <= 0 )
|
if( f.GetLine( sLine ) <= 0 )
|
||||||
THROW
|
THROW
|
||||||
@@ -307,7 +305,7 @@ bool Model::LoadMilkshapeAscii( CString sPath )
|
|||||||
FixSlashesInPlace( sTexturePath );
|
FixSlashesInPlace( sTexturePath );
|
||||||
CollapsePath( sTexturePath );
|
CollapsePath( sTexturePath );
|
||||||
if( IsAFile(sTexturePath) )
|
if( IsAFile(sTexturePath) )
|
||||||
Material.aniTexture.Load( sTexturePath );
|
Material.diffuse.Load( sTexturePath );
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
CString sError = ssprintf( "'%s' references a texture '%s' that does not exist", sPath.c_str(), sTexturePath.c_str() );
|
CString sError = ssprintf( "'%s' references a texture '%s' that does not exist", sPath.c_str(), sTexturePath.c_str() );
|
||||||
@@ -321,6 +319,20 @@ bool Model::LoadMilkshapeAscii( CString sPath )
|
|||||||
strcpy (szName, "");
|
strcpy (szName, "");
|
||||||
sscanf (sLine, "\"%[^\"]\"", szName);
|
sscanf (sLine, "\"%[^\"]\"", szName);
|
||||||
strcpy( Material.szAlphaTexture, szName );
|
strcpy( Material.szAlphaTexture, szName );
|
||||||
|
|
||||||
|
if( strcmp(Material.szAlphaTexture, "")!=0 )
|
||||||
|
{
|
||||||
|
CString sTexturePath = sDir + Material.szAlphaTexture;
|
||||||
|
FixSlashesInPlace( sTexturePath );
|
||||||
|
CollapsePath( sTexturePath );
|
||||||
|
if( IsAFile(sTexturePath) )
|
||||||
|
Material.alpha.Load( sTexturePath );
|
||||||
|
else
|
||||||
|
{
|
||||||
|
CString sError = ssprintf( "'%s' references a texture '%s' that does not exist", sPath.c_str(), sTexturePath.c_str() );
|
||||||
|
RageException::Throw( sError );
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -536,9 +548,9 @@ void Model::DrawPrimitives()
|
|||||||
msMesh *pMesh = &m_Meshes[i];
|
msMesh *pMesh = &m_Meshes[i];
|
||||||
RageModelVertexVector& TempVertices = m_vTempVerticesByBone[i];
|
RageModelVertexVector& TempVertices = m_vTempVerticesByBone[i];
|
||||||
|
|
||||||
// apply material
|
if( pMesh->nMaterialIndex != -1 ) // has a material
|
||||||
if( pMesh->nMaterialIndex != -1 )
|
|
||||||
{
|
{
|
||||||
|
// apply material
|
||||||
msMaterial& mat = m_Materials[ pMesh->nMaterialIndex ];
|
msMaterial& mat = m_Materials[ pMesh->nMaterialIndex ];
|
||||||
|
|
||||||
RageColor Emissive = mat.Emissive;
|
RageColor Emissive = mat.Emissive;
|
||||||
@@ -555,16 +567,33 @@ void Model::DrawPrimitives()
|
|||||||
Diffuse,
|
Diffuse,
|
||||||
mat.Specular,
|
mat.Specular,
|
||||||
mat.fShininess );
|
mat.fShininess );
|
||||||
DISPLAY->SetTexture( mat.aniTexture.GetCurrentTexture() );
|
|
||||||
DISPLAY->SetSphereEnironmentMapping( mat.bSphereMapped );
|
// render the first pass with texture 1
|
||||||
|
DISPLAY->SetTexture( mat.diffuse.ani.GetCurrentTexture() );
|
||||||
|
DISPLAY->SetSphereEnironmentMapping( mat.diffuse.bSphereMapped );
|
||||||
|
// UGLY: This overrides the Actor's BlendMode
|
||||||
|
DISPLAY->SetBlendMode( mat.diffuse.blendMode );
|
||||||
|
DISPLAY->DrawIndexedTriangles( &TempVertices[0], pMesh->Vertices.size(), (Uint16*)&pMesh->Triangles[0], pMesh->Triangles.size()*3 );
|
||||||
|
|
||||||
|
// render the second pass with texture 2
|
||||||
|
if( mat.alpha.ani.GetCurrentTexture() )
|
||||||
|
{
|
||||||
|
DISPLAY->SetTexture( mat.alpha.ani.GetCurrentTexture() );
|
||||||
|
DISPLAY->SetSphereEnironmentMapping( mat.alpha.bSphereMapped );
|
||||||
|
// UGLY: This overrides the Actor's BlendMode
|
||||||
|
DISPLAY->SetBlendMode( mat.alpha.blendMode );
|
||||||
|
DISPLAY->DrawIndexedTriangles( &TempVertices[0], pMesh->Vertices.size(), (Uint16*)&pMesh->Triangles[0], pMesh->Triangles.size()*3 );
|
||||||
|
}
|
||||||
|
|
||||||
|
DISPLAY->SetSphereEnironmentMapping( false );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
RageColor emissive( 0,0,0,0 );
|
const static RageColor emissive( 0,0,0,0 );
|
||||||
RageColor ambient( 0.2f,0.2f,0.2f,1 );
|
const static RageColor ambient( 0.2f,0.2f,0.2f,1 );
|
||||||
RageColor diffuse( 0.7f,0.7f,0.7f,1 );
|
const static RageColor diffuse( 0.7f,0.7f,0.7f,1 );
|
||||||
RageColor specular( 0.2f,0.2f,0.2f,1 );
|
const static RageColor specular( 0.2f,0.2f,0.2f,1 );
|
||||||
float shininess = 1;
|
const static float shininess = 1;
|
||||||
DISPLAY->SetMaterial(
|
DISPLAY->SetMaterial(
|
||||||
emissive,
|
emissive,
|
||||||
ambient,
|
ambient,
|
||||||
@@ -573,10 +602,8 @@ void Model::DrawPrimitives()
|
|||||||
shininess );
|
shininess );
|
||||||
DISPLAY->SetTexture( NULL );
|
DISPLAY->SetTexture( NULL );
|
||||||
DISPLAY->SetSphereEnironmentMapping( false );
|
DISPLAY->SetSphereEnironmentMapping( false );
|
||||||
}
|
|
||||||
|
|
||||||
DISPLAY->DrawIndexedTriangles( &TempVertices[0], pMesh->Vertices.size(), (Uint16*)&pMesh->Triangles[0], pMesh->Triangles.size()*3 );
|
DISPLAY->DrawIndexedTriangles( &TempVertices[0], pMesh->Vertices.size(), (Uint16*)&pMesh->Triangles[0], pMesh->Triangles.size()*3 );
|
||||||
DISPLAY->SetSphereEnironmentMapping( false );
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -611,7 +638,7 @@ void Model::DrawPrimitives()
|
|||||||
Diffuse,
|
Diffuse,
|
||||||
mat.Specular,
|
mat.Specular,
|
||||||
mat.fShininess );
|
mat.fShininess );
|
||||||
DISPLAY->SetTexture( mat.aniTexture.GetCurrentTexture() );
|
DISPLAY->SetTexture( mat.diffuse.ani.GetCurrentTexture() );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -854,20 +881,26 @@ void Model::Update( float fDelta )
|
|||||||
AdvanceFrame( fDelta );
|
AdvanceFrame( fDelta );
|
||||||
|
|
||||||
for( int i=0; i<(int)m_Materials.size(); i++ )
|
for( int i=0; i<(int)m_Materials.size(); i++ )
|
||||||
m_Materials[i].aniTexture.Update( fDelta );
|
{
|
||||||
|
m_Materials[i].diffuse.ani.Update( fDelta );
|
||||||
|
m_Materials[i].alpha.ani.Update( fDelta );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Model::SetState( int iNewState )
|
void Model::SetState( int iNewState )
|
||||||
{
|
{
|
||||||
for( int i=0; i<(int)m_Materials.size(); i++ )
|
for( int i=0; i<(int)m_Materials.size(); i++ )
|
||||||
m_Materials[i].aniTexture.SetState( iNewState );
|
{
|
||||||
|
m_Materials[i].diffuse.ani.SetState( iNewState );
|
||||||
|
m_Materials[i].alpha.ani.SetState( iNewState );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int Model::GetNumStates()
|
int Model::GetNumStates()
|
||||||
{
|
{
|
||||||
int iMaxStates = 0;
|
int iMaxStates = 0;
|
||||||
for( int i=0; i<(int)m_Materials.size(); i++ )
|
for( int i=0; i<(int)m_Materials.size(); i++ )
|
||||||
iMaxStates = max( iMaxStates, m_Materials[i].aniTexture.GetNumStates() );
|
iMaxStates = max( iMaxStates, m_Materials[i].diffuse.ani.GetNumStates() );
|
||||||
return iMaxStates;
|
return iMaxStates;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -122,3 +122,4 @@ void AnimatedTexture::Unload()
|
|||||||
iCurState = 0;
|
iCurState = 0;
|
||||||
fSecsIntoFrame = 0;
|
fSecsIntoFrame = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -81,6 +81,7 @@ typedef struct msMesh
|
|||||||
/* msMaterial */
|
/* msMaterial */
|
||||||
class RageTexture;
|
class RageTexture;
|
||||||
|
|
||||||
|
// merge this into Sprite?
|
||||||
struct AnimatedTexture
|
struct AnimatedTexture
|
||||||
{
|
{
|
||||||
AnimatedTexture();
|
AnimatedTexture();
|
||||||
@@ -118,8 +119,28 @@ typedef struct msMaterial
|
|||||||
char szDiffuseTexture[MS_MAX_PATH];
|
char szDiffuseTexture[MS_MAX_PATH];
|
||||||
char szAlphaTexture[MS_MAX_PATH]; // not used in SM. Use alpha in diffuse texture instead
|
char szAlphaTexture[MS_MAX_PATH]; // not used in SM. Use alpha in diffuse texture instead
|
||||||
int nName; // not used in SM. What is this for anyway?
|
int nName; // not used in SM. What is this for anyway?
|
||||||
AnimatedTexture aniTexture;
|
|
||||||
|
struct Texture
|
||||||
|
{
|
||||||
|
Texture()
|
||||||
|
{
|
||||||
|
bSphereMapped = false;
|
||||||
|
blendMode = BLEND_NORMAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Load( CString sFile )
|
||||||
|
{
|
||||||
|
ani.Load( sFile );
|
||||||
|
bSphereMapped = sFile.Find("sphere") != -1;
|
||||||
|
if( sFile.Find("add") != -1 )
|
||||||
|
blendMode = BLEND_ADD;
|
||||||
|
else
|
||||||
|
blendMode = BLEND_NORMAL;
|
||||||
|
};
|
||||||
|
AnimatedTexture ani;
|
||||||
bool bSphereMapped; // true of "sphere" appears in the material name
|
bool bSphereMapped; // true of "sphere" appears in the material name
|
||||||
|
BlendMode blendMode;
|
||||||
|
} diffuse, alpha;
|
||||||
} msMaterial;
|
} msMaterial;
|
||||||
|
|
||||||
/* msPositionKey */
|
/* msPositionKey */
|
||||||
|
|||||||
@@ -16,7 +16,7 @@
|
|||||||
* depend on RageDisplay (since that'd boost RDisplay.h a lot), so let's just
|
* depend on RageDisplay (since that'd boost RDisplay.h a lot), so let's just
|
||||||
* put this here. */
|
* put this here. */
|
||||||
enum GlowMode { GLOW_BRIGHTEN, GLOW_WHITEN };
|
enum GlowMode { GLOW_BRIGHTEN, GLOW_WHITEN };
|
||||||
enum BlendMode { BLEND_NORMAL, BLEND_ADD, BLEND_NO_EFFECT };
|
enum BlendMode { BLEND_NORMAL, BLEND_ADD, BLEND_NO_EFFECT, BLEND_INVALID };
|
||||||
|
|
||||||
|
|
||||||
struct RageVector2
|
struct RageVector2
|
||||||
|
|||||||
Reference in New Issue
Block a user