Got blending between materials working with texture atlases.

This commit is contained in:
David Williams 2008-01-16 19:51:47 +00:00
parent 98af071bdd
commit c013b100a2
9 changed files with 158 additions and 57 deletions

View File

@ -16,7 +16,7 @@ namespace Ogre
class IndexedSurfacePatch
{
public:
IndexedSurfacePatch();
IndexedSurfacePatch(bool allowDuplicateVertices);
~IndexedSurfacePatch();
void addTriangle(const SurfaceVertex& v0,const SurfaceVertex& v1,const SurfaceVertex& v2);
@ -27,6 +27,9 @@ namespace Ogre
std::vector<SurfaceVertex> m_vecVertices;
long int vertexIndices[OGRE_REGION_SIDE_LENGTH*2+1][OGRE_REGION_SIDE_LENGTH*2+1][OGRE_REGION_SIDE_LENGTH*2+1];
private:
bool m_AllowDuplicateVertices;
};
}

View File

@ -32,7 +32,7 @@ namespace Ogre
{
public:
SurfaceVertex();
SurfaceVertex(UIntVector3 positionToSet, float alphaToSet);
SurfaceVertex(UIntVector3 positionToSet, float materialToSet, float alphaToSet);
SurfaceVertex(UIntVector3 positionToSet, Vector3 normalToSet);
friend bool operator==(const SurfaceVertex& lhs, const SurfaceVertex& rhs);
@ -40,20 +40,22 @@ namespace Ogre
float getAlpha(void) const;
const SurfaceEdgeIterator& getEdge(void) const;
float getMaterial(void) const;
const Vector3& getNormal(void) const;
const UIntVector3& getPosition(void) const;
void setAlpha(float alphaToSet);
void setEdge(const SurfaceEdgeIterator& edgeToSet);
void setMaterial(float materialToSet);
void setNormal(const Vector3& normalToSet);
std::string toString(void) const;
private:
float alpha;
Vector3 normal;
private:
UIntVector3 position;
Vector3 normal;
float material;
float alpha;
SurfaceEdgeIterator edge;

View File

@ -4,11 +4,13 @@ struct v2f
float4 Color : COLOR;
float4 TexCoords : TEXCOORD0;
float4 Normal : TEXCOORD1;
float Alpha : TEXCOORD2;
float2 Alpha : TEXCOORD2;
};
float4 main(v2f IN, uniform sampler2D colourMap : TEXUNIT0) : COLOR
{
//return float4(IN.Alpha.y, 1.0f-IN.Alpha.y, 0.0f,1.0f);
float textureScalingFactor = 20.0f;
float textureSize = 512.0f;
float noOfTexturesPerDimension = 4.0;
@ -25,7 +27,7 @@ float4 main(v2f IN, uniform sampler2D colourMap : TEXUNIT0) : COLOR
IN.TexCoords /= noOfTexturesPerDimension;
//Next we compute the offset of the texture in the texture atlas
float material = floor(IN.Alpha);
float material = floor(IN.Alpha.x);
float y = floor(material / noOfTexturesPerDimension);
float x = fmod(material,noOfTexturesPerDimension);
float2 offset = float2(x,y);
@ -40,5 +42,5 @@ float4 main(v2f IN, uniform sampler2D colourMap : TEXUNIT0) : COLOR
float3 colourMapValue = colourMapValueXY + colourMapValueYZ + colourMapValueXZ;
//Return the result
return float4(colourMapValue*IN.Color.rgb,1.0);
return float4(colourMapValue*IN.Color.rgb*IN.Alpha.y,IN.Alpha.y);
}

View File

@ -2,7 +2,7 @@ struct a2v
{
float4 Position : POSITION; //in object space
float3 Normal : NORMAL;
float Alpha : TEXCOORD0;
float2 Alpha : TEXCOORD0;
};
struct v2f
@ -11,7 +11,7 @@ struct v2f
float4 Color : COLOR;
float4 TexCoords : TEXCOORD0;
float4 Normal : TEXCOORD1;
float Alpha : TEXCOORD2;
float2 Alpha : TEXCOORD2;
};
struct light
@ -94,6 +94,8 @@ v2f doWork(a2v IN, float4x4 world, float4x4 viewProj, float4 ambient, int iNoOfL
OUT.Position = mul(viewProj, OUT.Position);
OUT.Alpha = IN.Alpha;
//OUT.Material = IN.Material;
return OUT;
}

View File

@ -2,6 +2,12 @@ material TextureAtlasMaterial
{
technique
{
pass
{
ambient 0.0 0.0 0.0
diffuse 0.0 0.0 0.0
}
pass
{
vertex_program_ref TextureAtlasOneLightVertexProgram
@ -23,6 +29,9 @@ material TextureAtlasMaterial
texture texture_atlas.png
filtering none
}
depth_bias 1 1
scene_blend add
}
}
}

View File

@ -2,7 +2,8 @@
namespace Ogre
{
IndexedSurfacePatch::IndexedSurfacePatch()
IndexedSurfacePatch::IndexedSurfacePatch(bool allowDuplicateVertices)
:m_AllowDuplicateVertices(allowDuplicateVertices)
{
memset(vertexIndices,0xFF,sizeof(vertexIndices)); //0xFF is -1 as two's complement - this may not be portable...
}
@ -13,46 +14,50 @@ namespace Ogre
void IndexedSurfacePatch::addTriangle(const SurfaceVertex& v0,const SurfaceVertex& v1,const SurfaceVertex& v2)
{
long int index = vertexIndices[long int(v0.getPosition().x +0.5)][long int(v0.getPosition().y +0.5)][long int(v0.getPosition().z +0.5)];
if(index == -1)
if(!m_AllowDuplicateVertices)
{
long int index = vertexIndices[long int(v0.getPosition().x +0.5)][long int(v0.getPosition().y +0.5)][long int(v0.getPosition().z +0.5)];
if(index == -1)
{
m_vecVertices.push_back(v0);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
}
else
{
m_vecTriangleIndices.push_back(index);
}
index = vertexIndices[long int(v1.getPosition().x +0.5)][long int(v1.getPosition().y +0.5)][long int(v1.getPosition().z +0.5)];
if(index == -1)
{
m_vecVertices.push_back(v1);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
}
else
{
m_vecTriangleIndices.push_back(index);
}
index = vertexIndices[long int(v2.getPosition().x +0.5)][long int(v2.getPosition().y +0.5)][long int(v2.getPosition().z +0.5)];
if(index == -1)
{
m_vecVertices.push_back(v2);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
}
else
{
m_vecTriangleIndices.push_back(index);
}
}
else
{
m_vecVertices.push_back(v0);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
}
else
{
m_vecTriangleIndices.push_back(index);
}
index = vertexIndices[long int(v1.getPosition().x +0.5)][long int(v1.getPosition().y +0.5)][long int(v1.getPosition().z +0.5)];
if(index == -1)
{
m_vecVertices.push_back(v1);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
}
else
{
m_vecTriangleIndices.push_back(index);
}
index = vertexIndices[long int(v2.getPosition().x +0.5)][long int(v2.getPosition().y +0.5)][long int(v2.getPosition().z +0.5)];
if(index == -1)
{
m_vecVertices.push_back(v2);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
}
else
{
m_vecTriangleIndices.push_back(index);
}
/*m_vecVertices.push_back(v0);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
m_vecVertices.push_back(v1);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);
m_vecVertices.push_back(v2);
m_vecTriangleIndices.push_back(m_vecVertices.size()-1);*/
}
void IndexedSurfacePatch::fillVertexAndIndexData(std::vector<SurfaceVertex>& vecVertices, std::vector<ushort>& vecIndices)

View File

@ -147,8 +147,8 @@ namespace Ogre
//Generate the surface
//std::vector< std::vector<SurfaceVertex> > vertexData;
//std::vector< std::vector<SurfaceTriangle> > indexData;
IndexedSurfacePatch* singleMaterialPatch = new IndexedSurfacePatch;
IndexedSurfacePatch* multiMaterialPatch = new IndexedSurfacePatch;
IndexedSurfacePatch* singleMaterialPatch = new IndexedSurfacePatch(false);
IndexedSurfacePatch* multiMaterialPatch = new IndexedSurfacePatch(true);
generateMeshDataForRegion(regionX,regionY,regionZ, singleMaterialPatch, multiMaterialPatch);
@ -538,17 +538,81 @@ namespace Ogre
//If all the materials are the same, we just need one triangle for that material with all the alphas set high.
if((material0 == material1) && (material1 == material2))
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material0 + 0.1);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material1 + 0.1);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material2 + 0.1);
SurfaceVertex surfaceVertex0Alpha1(vertex0,material0 + 0.1,1.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material1 + 0.1,1.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material2 + 0.1,1.0);
singleMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
else if(material0 == material1)
{
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material0 + 0.1,1.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material0 + 0.1,1.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material0 + 0.1,0.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material2 + 0.1,0.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material2 + 0.1,0.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material2 + 0.1,1.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
}
else if(material0 == material2)
{
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material0 + 0.1,1.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material0 + 0.1,0.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material0 + 0.1,1.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material1 + 0.1,0.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material1 + 0.1,1.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material1 + 0.1,0.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
}
else if(material1 == material2)
{
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material1 + 0.1,0.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material1 + 0.1,1.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material1 + 0.1,1.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material0 + 0.1,1.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material0 + 0.1,0.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material0 + 0.1,0.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
}
else
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material0 + 0.1);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material1 + 0.1);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material2 + 0.1);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material0 + 0.1,1.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material0 + 0.1,0.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material0 + 0.1,0.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material1 + 0.1,0.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material1 + 0.1,1.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material1 + 0.1,0.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
{
SurfaceVertex surfaceVertex0Alpha1(vertex0,material2 + 0.1,0.0);
SurfaceVertex surfaceVertex1Alpha1(vertex1,material2 + 0.1,0.0);
SurfaceVertex surfaceVertex2Alpha1(vertex2,material2 + 0.1,1.0);
multiMaterialPatch->addTriangle(surfaceVertex0Alpha1, surfaceVertex1Alpha1, surfaceVertex2Alpha1);
}
}
//If there not all the same, we need one triangle for each unique material.
//We'll also need some vertices with low alphas for blending.

View File

@ -27,7 +27,8 @@ namespace Ogre
decl->removeAllElements();
decl->addElement(0, 0, VET_FLOAT3, VES_POSITION);
decl->addElement(0, 3 * sizeof(float), VET_FLOAT3, VES_NORMAL);
decl->addElement(0, 6 * sizeof(float), VET_FLOAT1, VES_TEXTURE_COORDINATES);
decl->addElement(0, 6 * sizeof(float), VET_FLOAT2, VES_TEXTURE_COORDINATES);
//decl->addElement(0, 7 * sizeof(float), VET_FLOAT1, VES_TEXTURE_COORDINATES);
this->setMaterial(material);
@ -95,7 +96,9 @@ namespace Ogre
*prPos++ = vertexIter->getNormal().y;
*prPos++ = vertexIter->getNormal().z;
*prPos++ = vertexIter->getAlpha();
*prPos++ = vertexIter->getMaterial();
*prPos++ = vertexIter->getAlpha();
if(vertexIter->getPosition().x < vaabMin.x)
vaabMin.x = vertexIter->getPosition().x;

View File

@ -11,8 +11,9 @@ namespace Ogre
{
}
SurfaceVertex::SurfaceVertex(UIntVector3 positionToSet, float alphaToSet)
:alpha(alphaToSet)
SurfaceVertex::SurfaceVertex(UIntVector3 positionToSet, float materialToSet, float alphaToSet)
:material(materialToSet)
,alpha(alphaToSet)
,position(positionToSet)
,m_uHash((position.x*(OGRE_REGION_SIDE_LENGTH*2+1)*(OGRE_REGION_SIDE_LENGTH*2+1)) + (position.y*(OGRE_REGION_SIDE_LENGTH*2+1)) + (position.z))
{
@ -31,6 +32,11 @@ namespace Ogre
return alpha;
}
float SurfaceVertex::getMaterial(void) const
{
return material;
}
const SurfaceEdgeIterator& SurfaceVertex::getEdge(void) const
{
return edge;
@ -51,6 +57,11 @@ namespace Ogre
alpha = alphaToSet;
}
void SurfaceVertex::setMaterial(float materialToSet)
{
material = materialToSet;
}
void SurfaceVertex::setEdge(const SurfaceEdgeIterator& edgeToSet)
{
edge = edgeToSet;