Work making CubicSurfaceExtractorWithNormals use 'isQuadNeeded'.

This commit is contained in:
unknown 2012-04-16 15:23:45 +02:00
parent a15c075c9b
commit 7d1d81c732
7 changed files with 52 additions and 26 deletions

View File

@ -23,7 +23,7 @@ freely, subject to the following restrictions:
#include "OpenGLWidget.h" #include "OpenGLWidget.h"
#include "PolyVoxCore/MaterialDensityPair.h" #include "PolyVoxCore/Material.h"
#include "PolyVoxCore/CubicSurfaceExtractorWithNormals.h" #include "PolyVoxCore/CubicSurfaceExtractorWithNormals.h"
#include "PolyVoxCore/SurfaceMesh.h" #include "PolyVoxCore/SurfaceMesh.h"
#include "PolyVoxCore/SimpleVolume.h" #include "PolyVoxCore/SimpleVolume.h"
@ -33,7 +33,7 @@ freely, subject to the following restrictions:
//Use the PolyVox namespace //Use the PolyVox namespace
using namespace PolyVox; using namespace PolyVox;
void createSphereInVolume(SimpleVolume<MaterialDensityPair44>& volData, float fRadius) void createSphereInVolume(SimpleVolume<Material8>& volData, float fRadius)
{ {
//This vector hold the position of the center of the volume //This vector hold the position of the center of the volume
Vector3DFloat v3dVolCenter(volData.getWidth() / 2, volData.getHeight() / 2, volData.getDepth() / 2); Vector3DFloat v3dVolCenter(volData.getWidth() / 2, volData.getHeight() / 2, volData.getDepth() / 2);
@ -50,22 +50,19 @@ void createSphereInVolume(SimpleVolume<MaterialDensityPair44>& volData, float fR
//And compute how far the current position is from the center of the volume //And compute how far the current position is from the center of the volume
float fDistToCenter = (v3dCurrentPos - v3dVolCenter).length(); float fDistToCenter = (v3dCurrentPos - v3dVolCenter).length();
uint8_t uDensity = 0;
uint8_t uMaterial = 0; uint8_t uMaterial = 0;
//If the current voxel is less than 'radius' units from the center then we make it solid. //If the current voxel is less than 'radius' units from the center then we make it solid.
if(fDistToCenter <= fRadius) if(fDistToCenter <= fRadius)
{ {
//Our new density value //Our new density value
uDensity = VoxelTypeTraits<MaterialDensityPair44>::maxDensity();
uMaterial = 1; uMaterial = 1;
} }
//Get the old voxel //Get the old voxel
MaterialDensityPair44 voxel = volData.getVoxelAt(x,y,z); Material8 voxel = volData.getVoxelAt(x,y,z);
//Modify the density and material //Modify the density and material
voxel.setDensity(uDensity);
voxel.setMaterial(uMaterial); voxel.setMaterial(uMaterial);
//Wrte the voxel value into the volume //Wrte the voxel value into the volume
@ -83,12 +80,12 @@ int main(int argc, char *argv[])
openGLWidget.show(); openGLWidget.show();
//Create an empty volume and then place a sphere in it //Create an empty volume and then place a sphere in it
SimpleVolume<MaterialDensityPair44> volData(PolyVox::Region(Vector3DInt32(0,0,0), Vector3DInt32(63, 63, 63))); SimpleVolume<Material8> volData(PolyVox::Region(Vector3DInt32(0,0,0), Vector3DInt32(63, 63, 63)));
createSphereInVolume(volData, 30); createSphereInVolume(volData, 30);
//Extract the surface //Extract the surface
SurfaceMesh<PositionMaterialNormal> mesh; SurfaceMesh<PositionMaterialNormal> mesh;
CubicSurfaceExtractorWithNormals<SimpleVolume, MaterialDensityPair44 > surfaceExtractor(&volData, volData.getEnclosingRegion(), &mesh); CubicSurfaceExtractorWithNormals<SimpleVolume, Material8 > surfaceExtractor(&volData, volData.getEnclosingRegion(), &mesh, Material8::isQuadNeeded);
surfaceExtractor.execute(); surfaceExtractor.execute();
//Pass the surface to the OpenGL window //Pass the surface to the OpenGL window

View File

@ -35,11 +35,13 @@ namespace PolyVox
class CubicSurfaceExtractorWithNormals class CubicSurfaceExtractorWithNormals
{ {
public: public:
CubicSurfaceExtractorWithNormals(VolumeType<VoxelType>* volData, Region region, SurfaceMesh<PositionMaterialNormal>* result); CubicSurfaceExtractorWithNormals(VolumeType<VoxelType>* volData, Region region, SurfaceMesh<PositionMaterialNormal>* result, polyvox_function<bool(VoxelType voxelInFront, VoxelType voxelBehind, float& materialToUse)> funcIsQuadNeededCallback);
void execute(); void execute();
private: private:
polyvox_function<bool(VoxelType voxel0, VoxelType voxel1, float& materialToUse)> m_funcIsQuadNeededCallback;
//The volume data and a sampler to access it. //The volume data and a sampler to access it.
VolumeType<VoxelType>* m_volData; VolumeType<VoxelType>* m_volData;
typename VolumeType<VoxelType>::Sampler m_sampVolume; typename VolumeType<VoxelType>::Sampler m_sampVolume;

View File

@ -24,12 +24,14 @@ freely, subject to the following restrictions:
namespace PolyVox namespace PolyVox
{ {
template< template<typename> class VolumeType, typename VoxelType> template< template<typename> class VolumeType, typename VoxelType>
CubicSurfaceExtractorWithNormals<VolumeType, VoxelType>::CubicSurfaceExtractorWithNormals(VolumeType<VoxelType>* volData, Region region, SurfaceMesh<PositionMaterialNormal>* result) CubicSurfaceExtractorWithNormals<VolumeType, VoxelType>::CubicSurfaceExtractorWithNormals(VolumeType<VoxelType>* volData, Region region, SurfaceMesh<PositionMaterialNormal>* result, polyvox_function<bool(VoxelType voxelInFront, VoxelType voxelBehind, float& materialToUse)> funcIsQuadNeededCallback)
:m_volData(volData) :m_volData(volData)
,m_sampVolume(volData) ,m_sampVolume(volData)
,m_meshCurrent(result) ,m_meshCurrent(result)
,m_regSizeInVoxels(region) ,m_regSizeInVoxels(region)
,m_funcIsQuadNeededCallback(funcIsQuadNeededCallback)
{ {
assert(m_funcIsQuadNeededCallback);
} }
template< template<typename> class VolumeType, typename VoxelType> template< template<typename> class VolumeType, typename VoxelType>
@ -48,12 +50,11 @@ namespace PolyVox
float regY = static_cast<float>(y - m_regSizeInVoxels.getLowerCorner().getY()); float regY = static_cast<float>(y - m_regSizeInVoxels.getLowerCorner().getY());
float regZ = static_cast<float>(z - m_regSizeInVoxels.getLowerCorner().getZ()); float regZ = static_cast<float>(z - m_regSizeInVoxels.getLowerCorner().getZ());
int currentVoxel = m_volData->getVoxelAt(x,y,z).getMaterial() != 0; float material = 0.0f;
int plusXVoxel = m_volData->getVoxelAt(x+1,y,z).getMaterial() != 0; if(m_funcIsQuadNeededCallback(m_volData->getVoxelAt(x,y,z), m_volData->getVoxelAt(x+1,y,z), material))
if(currentVoxel > plusXVoxel)
{ {
float material = static_cast<float>(m_volData->getVoxelAt(x,y,z).getMaterial()); material = static_cast<float>(m_volData->getVoxelAt(x,y,z).getMaterial());
uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ - 0.5f), Vector3DFloat(1.0f, 0.0f, 0.0f), material)); uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ - 0.5f), Vector3DFloat(1.0f, 0.0f, 0.0f), material));
uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(1.0f, 0.0f, 0.0f), material)); uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(1.0f, 0.0f, 0.0f), material));
@ -63,9 +64,9 @@ namespace PolyVox
m_meshCurrent->addTriangleCubic(v0,v2,v1); m_meshCurrent->addTriangleCubic(v0,v2,v1);
m_meshCurrent->addTriangleCubic(v1,v2,v3); m_meshCurrent->addTriangleCubic(v1,v2,v3);
} }
if(currentVoxel < plusXVoxel) if(m_funcIsQuadNeededCallback(m_volData->getVoxelAt(x+1,y,z), m_volData->getVoxelAt(x,y,z), material))
{ {
float material = static_cast<float>(m_volData->getVoxelAt(x+1,y,z).getMaterial()); material = static_cast<float>(m_volData->getVoxelAt(x+1,y,z).getMaterial());
uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ - 0.5f), Vector3DFloat(-1.0f, 0.0f, 0.0f), material)); uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ - 0.5f), Vector3DFloat(-1.0f, 0.0f, 0.0f), material));
uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(-1.0f, 0.0f, 0.0f), material)); uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX + 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(-1.0f, 0.0f, 0.0f), material));
@ -77,9 +78,9 @@ namespace PolyVox
} }
int plusYVoxel = m_volData->getVoxelAt(x,y+1,z).getMaterial() != 0; int plusYVoxel = m_volData->getVoxelAt(x,y+1,z).getMaterial() != 0;
if(currentVoxel > plusYVoxel) if(m_funcIsQuadNeededCallback(m_volData->getVoxelAt(x,y,z), m_volData->getVoxelAt(x,y+1,z), material))
{ {
float material = static_cast<float>(m_volData->getVoxelAt(x,y,z).getMaterial()); material = static_cast<float>(m_volData->getVoxelAt(x,y,z).getMaterial());
uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ - 0.5f), Vector3DFloat(0.0f, 1.0f, 0.0f), material)); uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ - 0.5f), Vector3DFloat(0.0f, 1.0f, 0.0f), material));
uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 1.0f, 0.0f), material)); uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 1.0f, 0.0f), material));
@ -89,9 +90,9 @@ namespace PolyVox
m_meshCurrent->addTriangleCubic(v0,v1,v2); m_meshCurrent->addTriangleCubic(v0,v1,v2);
m_meshCurrent->addTriangleCubic(v1,v3,v2); m_meshCurrent->addTriangleCubic(v1,v3,v2);
} }
if(currentVoxel < plusYVoxel) if(m_funcIsQuadNeededCallback(m_volData->getVoxelAt(x,y+1,z), m_volData->getVoxelAt(x,y,z), material))
{ {
float material = static_cast<float>(m_volData->getVoxelAt(x,y+1,z).getMaterial()); material = static_cast<float>(m_volData->getVoxelAt(x,y+1,z).getMaterial());
uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ - 0.5f), Vector3DFloat(0.0f, -1.0f, 0.0f), material)); uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ - 0.5f), Vector3DFloat(0.0f, -1.0f, 0.0f), material));
uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, -1.0f, 0.0f), material)); uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, -1.0f, 0.0f), material));
@ -103,9 +104,9 @@ namespace PolyVox
} }
int plusZVoxel = m_volData->getVoxelAt(x,y,z+1).getMaterial() != 0; int plusZVoxel = m_volData->getVoxelAt(x,y,z+1).getMaterial() != 0;
if(currentVoxel > plusZVoxel) if(m_funcIsQuadNeededCallback(m_volData->getVoxelAt(x,y,z), m_volData->getVoxelAt(x,y,z+1), material))
{ {
float material = static_cast<float>(m_volData->getVoxelAt(x,y,z).getMaterial()); material = static_cast<float>(m_volData->getVoxelAt(x,y,z).getMaterial());
uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, 1.0f), material)); uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, 1.0f), material));
uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, 1.0f), material)); uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, 1.0f), material));
@ -115,9 +116,9 @@ namespace PolyVox
m_meshCurrent->addTriangleCubic(v0,v2,v1); m_meshCurrent->addTriangleCubic(v0,v2,v1);
m_meshCurrent->addTriangleCubic(v1,v2,v3); m_meshCurrent->addTriangleCubic(v1,v2,v3);
} }
if(currentVoxel < plusZVoxel) if(m_funcIsQuadNeededCallback(m_volData->getVoxelAt(x,y,z+1), m_volData->getVoxelAt(x,y,z), material))
{ {
float material = static_cast<float>(m_volData->getVoxelAt(x,y,z+1).getMaterial()); material = static_cast<float>(m_volData->getVoxelAt(x,y,z+1).getMaterial());
uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, -1.0f), material)); uint32_t v0 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY - 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, -1.0f), material));
uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, -1.0f), material)); uint32_t v1 = m_meshCurrent->addVertex(PositionMaterialNormal(Vector3DFloat(regX - 0.5f, regY + 0.5f, regZ + 0.5f), Vector3DFloat(0.0f, 0.0f, -1.0f), material));

View File

@ -96,6 +96,19 @@ namespace PolyVox
//static DensityType getminDensity()() throw() { return 0; } //static DensityType getminDensity()() throw() { return 0; }
static DensityType getThreshold() throw() { return 1; } static DensityType getThreshold() throw() { return 1; }
static bool isQuadNeeded(Material<Type> from, Material<Type> to, float& materialToUse)
{
if((from.getMaterial() > 0) && (to.getMaterial() == 0))
{
materialToUse = static_cast<float>(from.getMaterial());
return true;
}
else
{
return false;
}
}
private: private:
MaterialType m_uMaterial; MaterialType m_uMaterial;
}; };

View File

@ -78,6 +78,19 @@ namespace PolyVox
//static DensityType getminDensity()() throw() { return 0; } //static DensityType getminDensity()() throw() { return 0; }
static DensityType getThreshold() throw() {return 0x01 << (NoOfDensityBits - 1);} static DensityType getThreshold() throw() {return 0x01 << (NoOfDensityBits - 1);}
static bool isQuadNeeded(MaterialDensityPair<Type, NoOfMaterialBits, NoOfDensityBits> from, MaterialDensityPair<Type, NoOfMaterialBits, NoOfDensityBits> to, float& materialToUse)
{
if((from.getMaterial() > 0) && (to.getMaterial() == 0))
{
materialToUse = static_cast<float>(from.getMaterial());
return true;
}
else
{
return false;
}
}
private: private:
MaterialType m_uMaterial : NoOfMaterialBits; MaterialType m_uMaterial : NoOfMaterialBits;
DensityType m_uDensity : NoOfDensityBits; DensityType m_uDensity : NoOfDensityBits;

View File

@ -31,7 +31,7 @@ namespace PolyVox
{ {
void extractCubicMesh(Volume& volume, const Region& region, Mesh& resultMesh) void extractCubicMesh(Volume& volume, const Region& region, Mesh& resultMesh)
{ {
CubicSurfaceExtractorWithNormals<SimpleVolume, MaterialDensityPair88 > surfaceExtractor(&volume, region, &resultMesh); CubicSurfaceExtractorWithNormals<SimpleVolume, MaterialDensityPair88 > surfaceExtractor(&volume, region, &resultMesh, MaterialDensityPair88::isQuadNeeded);
surfaceExtractor.execute(); surfaceExtractor.execute();
} }

View File

@ -94,7 +94,7 @@ void testForType(SurfaceMesh<PositionMaterialNormal>& result)
} }
} }
CubicSurfaceExtractorWithNormals<SimpleVolume, VoxelType > extractor(&volData, volData.getEnclosingRegion(), &result, 50); CubicSurfaceExtractorWithNormals<SimpleVolume, VoxelType > extractor(&volData, volData.getEnclosingRegion(), &result, VoxelType::isQuadNeeded);
extractor.execute(); extractor.execute();
} }