Changed interface to SurfaceExtractor.
This commit is contained in:
parent
854c8b6fa4
commit
85e5a27457
@ -82,17 +82,18 @@ Now that we have built our volume we need to convert it into a triangle mesh for
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
SurfaceExtractor<MaterialDensityPair44> surfaceExtractor(volData);
|
||||
SurfaceMesh mesh;
|
||||
SurfaceExtractor<MaterialDensityPair44> surfaceExtractor(&volData, volData.getEnclosingRegion(), &mesh);
|
||||
|
||||
Again, note thiat this class is templatised on the voxel type. It also takes a reference to the Volume on which the surface extraction will be performed.
|
||||
The SurfaceExtractor takes a pointer to the volume data, and also it needs to be told which Region of the Volume the extraction should be performed on (in more advanced application this is useful for extracting only those parts of the volume which have been modified since the last extraction). For our purposes the Volume class provides a convienient Volume::getEnclosingRegion() function which returns a Region representing the whole volume. The constructor also takes a pointer to a SurfaceMesh object whiere it will store the result, so we need to create one of these before we can construct the SurfaceExtractor.
|
||||
|
||||
The actual extraction happens in the SurfaceExtractor::extractSurfaceForRegion() function. This function needs to be told which Region of the Volume the extraction should be performed on (in more advanced application this is useful for extracting only those parts of the volume which have been modified since the last extraction), but for our purposes the Volume class provides a convienient Volume::getEnclosingRegion() function which returns a Region representing the whole volume.
|
||||
The actual extraction happens in the SurfaceExtractor::execute() function. This means you can set up your SurfaceExtractor with the required parameters and then actually execute it later (on a different thread, perhaps). For this example we just call it straight away.
|
||||
|
||||
.. code-block:: c++
|
||||
|
||||
shared_ptr<SurfaceMesh> surface = surfaceExtractor.extractSurfaceForRegion(volData.getEnclosingRegion());
|
||||
surfaceExtractor.execute();
|
||||
|
||||
The result is a SurfaceMesh object, which basically contains an index and vertex buffer representing the desired triangle mesh. This is returned via a shared_ptr, meaning it will automatically be deleted once there are no remaining references to it.
|
||||
This fills in our SurfaceMesh object, which basically contains an index and vertex buffer representing the desired triangle mesh.
|
||||
|
||||
Rendering the surface
|
||||
=====================
|
||||
|
@ -82,11 +82,12 @@ int main(int argc, char *argv[])
|
||||
createSphereInVolume(volData, 30);
|
||||
|
||||
//Extract the surface
|
||||
SurfaceExtractor<MaterialDensityPair44> surfaceExtractor(volData);
|
||||
shared_ptr<SurfaceMesh> surface = surfaceExtractor.extractSurfaceForRegion(volData.getEnclosingRegion());
|
||||
SurfaceMesh mesh;
|
||||
SurfaceExtractor<MaterialDensityPair44> surfaceExtractor(&volData, volData.getEnclosingRegion(), &mesh);
|
||||
surfaceExtractor.execute();
|
||||
|
||||
//Pass the surface to the OpenGL window
|
||||
openGLWidget.setSurfaceMeshToRender(*surface);
|
||||
openGLWidget.setSurfaceMeshToRender(mesh);
|
||||
|
||||
//Run the message pump.
|
||||
return app.exec();
|
||||
|
@ -63,8 +63,6 @@ void OpenGLWidget::setVolume(PolyVox::Volume<MaterialDensityPair44>* volData)
|
||||
m_uVolumeHeightInRegions = volData->getHeight() / m_uRegionSideLength;
|
||||
m_uVolumeDepthInRegions = volData->getDepth() / m_uRegionSideLength;
|
||||
|
||||
SurfaceExtractor<MaterialDensityPair44> surfaceExtractor(*volData);
|
||||
|
||||
//Our volume is broken down into cuboid regions, and we create one mesh for each region.
|
||||
//This three-level for loop iterates over each region.
|
||||
for(uint16_t uRegionZ = 0; uRegionZ < m_uVolumeDepthInRegions; ++uRegionZ)
|
||||
@ -90,7 +88,10 @@ void OpenGLWidget::setVolume(PolyVox::Volume<MaterialDensityPair44>* volData)
|
||||
|
||||
//Extract the surface for this region
|
||||
//extractSurface(m_volData, 0, PolyVox::Region(regLowerCorner, regUpperCorner), meshCurrent);
|
||||
shared_ptr<SurfaceMesh> mesh = surfaceExtractor.extractSurfaceForRegion(PolyVox::Region(regLowerCorner, regUpperCorner));
|
||||
|
||||
shared_ptr<SurfaceMesh> mesh(new SurfaceMesh);
|
||||
SurfaceExtractor<MaterialDensityPair44> surfaceExtractor(volData, PolyVox::Region(regLowerCorner, regUpperCorner), mesh.get());
|
||||
surfaceExtractor.execute();
|
||||
|
||||
//computeNormalsForVertices(m_volData, *(mesh.get()), SOBEL_SMOOTHED);
|
||||
//*meshCurrent = getSmoothedSurface(*meshCurrent);
|
||||
|
@ -39,9 +39,9 @@ namespace PolyVox
|
||||
class SurfaceExtractor
|
||||
{
|
||||
public:
|
||||
SurfaceExtractor(Volume<VoxelType>& volData);
|
||||
SurfaceExtractor(Volume<VoxelType>* volData, Region region, SurfaceMesh* result);
|
||||
|
||||
std::shared_ptr<SurfaceMesh> extractSurfaceForRegion(Region region);
|
||||
void execute();
|
||||
|
||||
private:
|
||||
//Compute the cell bitmask for a particular slice in z.
|
||||
@ -71,7 +71,7 @@ namespace PolyVox
|
||||
const Array2DInt32& m_pCurrentVertexIndicesZ);
|
||||
|
||||
//The volume data and a sampler to access it.
|
||||
Volume<VoxelType> m_volData;
|
||||
Volume<VoxelType>* m_volData;
|
||||
VolumeSampler<VoxelType> m_sampVolume;
|
||||
|
||||
//Holds a position in volume space.
|
||||
@ -91,6 +91,7 @@ namespace PolyVox
|
||||
SurfaceMesh* m_meshCurrent;
|
||||
|
||||
//Information about the region we are currently processing
|
||||
Region m_regInput;
|
||||
Region m_regInputCropped;
|
||||
Region m_regInputUncropped;
|
||||
Region m_regVolumeCropped;
|
||||
|
@ -32,27 +32,29 @@ using namespace std;
|
||||
namespace PolyVox
|
||||
{
|
||||
template <typename VoxelType>
|
||||
SurfaceExtractor<VoxelType>::SurfaceExtractor(Volume<VoxelType>& volData)
|
||||
SurfaceExtractor<VoxelType>::SurfaceExtractor(Volume<VoxelType>* volData, Region region, SurfaceMesh* result)
|
||||
:m_volData(volData)
|
||||
,m_sampVolume(&volData)
|
||||
,m_sampVolume(volData)
|
||||
,m_regInput(region)
|
||||
,m_meshCurrent(result)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename VoxelType>
|
||||
shared_ptr<SurfaceMesh> SurfaceExtractor<VoxelType>::extractSurfaceForRegion(Region region)
|
||||
void SurfaceExtractor<VoxelType>::execute()
|
||||
{
|
||||
m_regInputUncropped = region;
|
||||
m_regInputUncropped = m_regInput;
|
||||
|
||||
//When generating the mesh for a region we actually look outside it in the
|
||||
// back, bottom, right direction. Protect against access violations by cropping region here
|
||||
m_regVolumeCropped = m_volData.getEnclosingRegion();
|
||||
m_regVolumeCropped = m_volData->getEnclosingRegion();
|
||||
m_regInputUncropped.cropTo(m_regVolumeCropped);
|
||||
m_regVolumeCropped.setUpperCorner(m_regVolumeCropped.getUpperCorner() - Vector3DInt16(1,1,1));
|
||||
|
||||
m_regInputCropped = region;
|
||||
m_regInputCropped = m_regInput;
|
||||
m_regInputCropped.cropTo(m_regVolumeCropped);
|
||||
|
||||
m_meshCurrent = new SurfaceMesh();
|
||||
//m_meshCurrent = new SurfaceMesh();
|
||||
|
||||
m_uRegionWidth = m_regInputCropped.width();
|
||||
m_uRegionHeight = m_regInputCropped.height();
|
||||
@ -147,8 +149,6 @@ namespace PolyVox
|
||||
lodRecord.beginIndex = 0;
|
||||
lodRecord.endIndex = m_meshCurrent->getNoOfIndices();
|
||||
m_meshCurrent->m_vecLodRecords.push_back(lodRecord);
|
||||
|
||||
return shared_ptr<SurfaceMesh>(m_meshCurrent);
|
||||
}
|
||||
|
||||
template<typename VoxelType>
|
||||
|
Loading…
x
Reference in New Issue
Block a user