Tidying up and refactoring LargeVolume.

This commit is contained in:
Daviw Williams
2013-06-26 17:02:06 +02:00
parent 8ab6d73f0a
commit 44d525f591
4 changed files with 55 additions and 39 deletions

View File

@ -82,11 +82,11 @@ int main(int argc, char *argv[])
//Create an empty volume and then place a sphere in it //Create an empty volume and then place a sphere in it
RLECompressor<uint8_t, uint16_t>* pCompressor = new RLECompressor<uint8_t, uint16_t>(); RLECompressor<uint8_t, uint16_t>* pCompressor = new RLECompressor<uint8_t, uint16_t>();
FilePager<uint8_t>* pFilePager = new FilePager<uint8_t>("D:/temp/voldata/"); FilePager<uint8_t>* pFilePager = new FilePager<uint8_t>("C:/temp/voldata/");
LargeVolume<uint8_t> volData(PolyVox::Region(Vector3DInt32(0,0,0), Vector3DInt32(63, 63, 63)), pCompressor, pFilePager, 32); LargeVolume<uint8_t> volData(PolyVox::Region(Vector3DInt32(0,0,0), Vector3DInt32(63, 63, 63)), pCompressor, pFilePager, 32);
volData.setMaxNumberOfUncompressedBlocks(6); volData.setMaxNumberOfUncompressedBlocks(2);
volData.setMaxNumberOfBlocksInMemory(7); volData.setMaxNumberOfBlocksInMemory(4);
createSphereInVolume(volData, 30); createSphereInVolume(volData, 30);

View File

@ -332,7 +332,7 @@ int main(int argc, char *argv[])
//If these lines don't compile, please try commenting them out and using the two lines after //If these lines don't compile, please try commenting them out and using the two lines after
//(you will need Boost for this). If you have to do this then please let us know in the forums as //(you will need Boost for this). If you have to do this then please let us know in the forums as
//we rely on community feedback to keep the Boost version running. //we rely on community feedback to keep the Boost version running.
LargeVolume<MaterialDensityPair44> volData(compressor, pager, 256); LargeVolume<MaterialDensityPair44> volData(Region::MaxRegion, compressor, pager, 256);
//LargeVolume<MaterialDensityPair44> volData(polyvox_bind(&load, polyvox_placeholder_1, polyvox_placeholder_2), //LargeVolume<MaterialDensityPair44> volData(polyvox_bind(&load, polyvox_placeholder_1, polyvox_placeholder_2),
// polyvox_bind(&unload, polyvox_placeholder_1, polyvox_placeholder_2), 256); // polyvox_bind(&unload, polyvox_placeholder_1, polyvox_placeholder_2), 256);
volData.setMaxNumberOfBlocksInMemory(4096); volData.setMaxNumberOfBlocksInMemory(4096);

View File

@ -234,11 +234,10 @@ namespace PolyVox
#endif #endif
public: public:
/// Constructor for creating a very large paging volume. /// Constructor for creating a fixed size volume.
LargeVolume LargeVolume
( (
Compressor* pCompressor, const Region& regValid,
Pager<VoxelType>* pPager,
uint16_t uBlockSideLength = 32 uint16_t uBlockSideLength = 32
); );
/// Constructor for creating a fixed size volume. /// Constructor for creating a fixed size volume.
@ -246,7 +245,7 @@ namespace PolyVox
( (
const Region& regValid, const Region& regValid,
Compressor* pCompressor, Compressor* pCompressor,
Pager<VoxelType>* pPager, Pager<VoxelType>* pPager ,
uint16_t uBlockSideLength = 32 uint16_t uBlockSideLength = 32
); );
/// Destructor /// Destructor
@ -319,7 +318,7 @@ namespace PolyVox
return false; return false;
} }
}; };
void initialise(const Region& regValidRegion, uint16_t uBlockSideLength); void initialise();
// A trick to implement specialization of template member functions in template classes. See http://stackoverflow.com/a/4951057 // A trick to implement specialization of template member functions in template classes. See http://stackoverflow.com/a/4951057
template <WrapMode eWrapMode> template <WrapMode eWrapMode>
@ -344,13 +343,13 @@ namespace PolyVox
/// this function can be called by m_funcDataRequiredHandler without causing any weird effects /// this function can be called by m_funcDataRequiredHandler without causing any weird effects
bool setVoxelAtConst(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tValue) const; bool setVoxelAtConst(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tValue) const;
//The block data // The block data
mutable std::map<Vector3DInt32, Block<VoxelType>, BlockPositionCompare> m_pBlocks; mutable std::map<Vector3DInt32, Block<VoxelType>, BlockPositionCompare> m_pBlocks;
//The cache of uncompressed blocks. The uncompressed block data and the timestamps are stored here rather // The cache of uncompressed blocks. The uncompressed block data and the timestamps are stored here rather
//than in the Block class. This is so that in the future each VolumeIterator might to maintain its own cache // than in the Block class. This is so that in the future each VolumeIterator might to maintain its own cache
//of blocks. However, this could mean the same block data is uncompressed and modified in more than one // of blocks. However, this could mean the same block data is uncompressed and modified in more than one
//location in memory... could be messy with threading. // location in memory... could be messy with threading.
mutable std::vector< Block<VoxelType>* > m_vecBlocksWithUncompressedData; mutable std::vector< Block<VoxelType>* > m_vecBlocksWithUncompressedData;
mutable uint32_t m_uTimestamper; mutable uint32_t m_uTimestamper;
mutable Vector3DInt32 m_v3dLastAccessedBlockPos; mutable Vector3DInt32 m_v3dLastAccessedBlockPos;
@ -358,16 +357,20 @@ namespace PolyVox
uint32_t m_uMaxNumberOfUncompressedBlocks; uint32_t m_uMaxNumberOfUncompressedBlocks;
uint32_t m_uMaxNumberOfBlocksInMemory; uint32_t m_uMaxNumberOfBlocksInMemory;
//The size of the volume // The size of the volume
Region m_regValidRegionInBlocks; Region m_regValidRegionInBlocks;
//The size of the blocks // The size of the blocks
uint16_t m_uBlockSideLength; uint16_t m_uBlockSideLength;
uint8_t m_uBlockSideLengthPower; uint8_t m_uBlockSideLengthPower;
//The compressor used by the Blocks to compress their data if required. // The compressor used by the Blocks to compress their data if required.
Compressor* m_pCompressor; Compressor* m_pCompressor;
Pager<VoxelType>* m_pPager; Pager<VoxelType>* m_pPager;
// Whether we created the compressor or whether it was provided
// by the user. This controls whether we delete it on destruction.
bool m_bIsOurCompressor;
}; };
} }

View File

@ -23,6 +23,8 @@ freely, subject to the following restrictions:
#include "PolyVoxCore/Impl/ErrorHandling.h" #include "PolyVoxCore/Impl/ErrorHandling.h"
#include "PolyVoxCore/MinizCompressor.h"
//Included here rather than in the .h because it refers to LargeVolume (avoids forward declaration) //Included here rather than in the .h because it refers to LargeVolume (avoids forward declaration)
#include "PolyVoxCore/ConstVolumeProxy.h" #include "PolyVoxCore/ConstVolumeProxy.h"
@ -37,16 +39,19 @@ namespace PolyVox
template <typename VoxelType> template <typename VoxelType>
LargeVolume<VoxelType>::LargeVolume LargeVolume<VoxelType>::LargeVolume
( (
Compressor* pCompressor, const Region& regValid,
Pager<VoxelType>* pPager,
uint16_t uBlockSideLength uint16_t uBlockSideLength
) )
:BaseVolume<VoxelType>(Region::MaxRegion) :BaseVolume<VoxelType>(regValid)
,m_pCompressor(pCompressor)
{ {
m_pPager = pPager; m_uBlockSideLength = uBlockSideLength;
//Create a volume of the right size.
initialise(Region::MaxRegion,uBlockSideLength); m_pCompressor = new MinizCompressor();
m_bIsOurCompressor = true;
m_pPager = 0;
initialise();
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -67,12 +72,16 @@ namespace PolyVox
uint16_t uBlockSideLength uint16_t uBlockSideLength
) )
:BaseVolume<VoxelType>(regValid) :BaseVolume<VoxelType>(regValid)
,m_pCompressor(pCompressor)
{ {
m_uBlockSideLength = uBlockSideLength;
m_pCompressor = pCompressor;
m_bIsOurCompressor = false;
m_pPager = pPager; m_pPager = pPager;
//Create a volume of the right size. initialise();
initialise(regValid,uBlockSideLength);
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -95,6 +104,12 @@ namespace PolyVox
LargeVolume<VoxelType>::~LargeVolume() LargeVolume<VoxelType>::~LargeVolume()
{ {
flushAll(); flushAll();
// Only delete the compressor if it was created by us (in the constructor), not by the user.
if(m_bIsOurCompressor)
{
delete m_pCompressor;
}
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -480,33 +495,31 @@ namespace PolyVox
/// This function should probably be made internal... /// This function should probably be made internal...
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
template <typename VoxelType> template <typename VoxelType>
void LargeVolume<VoxelType>::initialise(const Region& regValidRegion, uint16_t uBlockSideLength) void LargeVolume<VoxelType>::initialise()
{ {
//Validate parameters //Validate parameters
if(uBlockSideLength == 0) if(m_uBlockSideLength == 0)
{ {
POLYVOX_THROW(std::invalid_argument, "Block side length cannot be zero."); POLYVOX_THROW(std::invalid_argument, "Block side length cannot be zero.");
} }
if(!isPowerOf2(uBlockSideLength))
if(!isPowerOf2(m_uBlockSideLength))
{ {
POLYVOX_THROW(std::invalid_argument, "Block side length must be a power of two."); POLYVOX_THROW(std::invalid_argument, "Block side length must be a power of two.");
} }
if(!m_pCompressor) if(!m_pCompressor)
{ {
POLYVOX_THROW(std::invalid_argument, "You must provide a compressor for the LargeVolume to use."); POLYVOX_THROW(std::invalid_argument, "You must provide a valid compressor for the LargeVolume to use.");
} }
m_uTimestamper = 0; m_uTimestamper = 0;
m_uMaxNumberOfUncompressedBlocks = 16; m_uMaxNumberOfUncompressedBlocks = 16;
m_uBlockSideLength = uBlockSideLength;
m_uMaxNumberOfBlocksInMemory = 1024; m_uMaxNumberOfBlocksInMemory = 1024;
m_v3dLastAccessedBlockPos = Vector3DInt32(0,0,0); //There are no invalid positions, but initially the m_pLastAccessedBlock pointer will be null; m_v3dLastAccessedBlockPos = Vector3DInt32(0,0,0); //There are no invalid positions, but initially the m_pLastAccessedBlock pointer will be null;
m_pLastAccessedBlock = 0; m_pLastAccessedBlock = 0;
this->m_regValidRegion = regValidRegion;
//Compute the block side length //Compute the block side length
m_uBlockSideLength = uBlockSideLength;
m_uBlockSideLengthPower = logBase2(m_uBlockSideLength); m_uBlockSideLengthPower = logBase2(m_uBlockSideLength);
m_regValidRegionInBlocks.setLowerX(this->m_regValidRegion.getLowerX() >> m_uBlockSideLengthPower); m_regValidRegionInBlocks.setLowerX(this->m_regValidRegion.getLowerX() >> m_uBlockSideLengthPower);