Properly implemented Volume::tidyUpMemory().
This commit is contained in:
parent
df68b1fe7a
commit
8f0ca490df
@ -66,7 +66,7 @@ int main(int argc, char *argv[])
|
|||||||
createCubeInVolume(volData, Vector3DUint16(midPos+1, minPos, midPos+1), Vector3DUint16(maxPos, midPos-1, maxPos), 0);
|
createCubeInVolume(volData, Vector3DUint16(midPos+1, minPos, midPos+1), Vector3DUint16(maxPos, midPos-1, maxPos), 0);
|
||||||
createCubeInVolume(volData, Vector3DUint16(minPos, midPos+1, midPos+1), Vector3DUint16(midPos-1, maxPos, maxPos), 0);
|
createCubeInVolume(volData, Vector3DUint16(minPos, midPos+1, midPos+1), Vector3DUint16(midPos-1, maxPos, maxPos), 0);
|
||||||
|
|
||||||
volData.idle(0);
|
volData.tidyUpMemory(0);
|
||||||
|
|
||||||
QApplication app(argc, argv);
|
QApplication app(argc, argv);
|
||||||
|
|
||||||
|
@ -28,6 +28,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|||||||
|
|
||||||
#include "PolyVoxImpl/CPlusPlusZeroXSupport.h"
|
#include "PolyVoxImpl/CPlusPlusZeroXSupport.h"
|
||||||
|
|
||||||
|
#include <limits>
|
||||||
#include <map>
|
#include <map>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
@ -56,7 +57,7 @@ namespace PolyVox
|
|||||||
void setVoxelAt(uint16_t uXPos, uint16_t uYPos, uint16_t uZPos, VoxelType tValue);
|
void setVoxelAt(uint16_t uXPos, uint16_t uYPos, uint16_t uZPos, VoxelType tValue);
|
||||||
void setVoxelAt(const Vector3DUint16& v3dPos, VoxelType tValue);
|
void setVoxelAt(const Vector3DUint16& v3dPos, VoxelType tValue);
|
||||||
|
|
||||||
void idle(uint32_t uAmount);
|
void tidyUpMemory(uint32_t uNoOfBlocksToProcess = numeric_limits<uint32_t>::max);
|
||||||
bool isRegionHomogenous(const Region& region);
|
bool isRegionHomogenous(const Region& region);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
@ -80,6 +81,8 @@ namespace PolyVox
|
|||||||
|
|
||||||
uint8_t m_uBlockSideLengthPower;
|
uint8_t m_uBlockSideLengthPower;
|
||||||
uint16_t m_uBlockSideLength;
|
uint16_t m_uBlockSideLength;
|
||||||
|
|
||||||
|
uint32_t m_uCurrentBlockForTidying;
|
||||||
};
|
};
|
||||||
|
|
||||||
//Required for the static member
|
//Required for the static member
|
||||||
|
@ -38,6 +38,7 @@ namespace PolyVox
|
|||||||
template <typename VoxelType>
|
template <typename VoxelType>
|
||||||
Volume<VoxelType>::Volume(uint16_t uSideLength, uint16_t uBlockSideLength)
|
Volume<VoxelType>::Volume(uint16_t uSideLength, uint16_t uBlockSideLength)
|
||||||
:m_pBlocks(0)
|
:m_pBlocks(0)
|
||||||
|
,m_uCurrentBlockForTidying(0)
|
||||||
{
|
{
|
||||||
//Debug mode validation
|
//Debug mode validation
|
||||||
assert(isPowerOf2(uSideLength));
|
assert(isPowerOf2(uSideLength));
|
||||||
@ -201,37 +202,56 @@ namespace PolyVox
|
|||||||
|
|
||||||
#pragma region Other
|
#pragma region Other
|
||||||
template <typename VoxelType>
|
template <typename VoxelType>
|
||||||
void Volume<VoxelType>::idle(uint32_t uAmount)
|
void Volume<VoxelType>::tidyUpMemory(uint32_t uNoOfBlocksToProcess)
|
||||||
{
|
{
|
||||||
for(uint32_t i = 0; i < m_uNoOfBlocksInVolume; ++i)
|
//Track the number of blocks we have processed.
|
||||||
{
|
uint32_t m_uNoOfProcessedBlocks = 0;
|
||||||
if(m_vecBlockIsPotentiallyHomogenous[i])
|
|
||||||
{
|
|
||||||
if(m_pBlocks[i].m_pBlockData->isHomogeneous())
|
|
||||||
{
|
|
||||||
VoxelType homogeneousValue = m_pBlocks[i].m_pBlockData->getVoxelAt(0,0,0);
|
|
||||||
|
|
||||||
m_pBlocks[i].m_pBlockData = getHomogenousBlockData(homogeneousValue);
|
//We will loop around, and finish if we get back to our start position
|
||||||
|
uint32_t uFinishBlock = m_uCurrentBlockForTidying;
|
||||||
|
|
||||||
|
//Increment the current block, looping around if necessary
|
||||||
|
++m_uCurrentBlockForTidying;
|
||||||
|
m_uCurrentBlockForTidying %= m_uNoOfBlocksInVolume;
|
||||||
|
|
||||||
|
//While we have not reached the user specified limit and there are more blocks to process...
|
||||||
|
while((m_uNoOfProcessedBlocks < uNoOfBlocksToProcess) && (m_uCurrentBlockForTidying != uFinishBlock))
|
||||||
|
{
|
||||||
|
//We only do any work if the block is flagged as potentially homogeneous.
|
||||||
|
if(m_vecBlockIsPotentiallyHomogenous[m_uCurrentBlockForTidying])
|
||||||
|
{
|
||||||
|
//Check if it's really homogeneous (this can be slow).
|
||||||
|
if(m_pBlocks[m_uCurrentBlockForTidying].m_pBlockData->isHomogeneous())
|
||||||
|
{
|
||||||
|
//If so, replace is with a block from out homogeneous collection.
|
||||||
|
VoxelType homogeneousValue = m_pBlocks[m_uCurrentBlockForTidying].m_pBlockData->getVoxelAt(0,0,0);
|
||||||
|
m_pBlocks[m_uCurrentBlockForTidying].m_pBlockData = getHomogenousBlockData(homogeneousValue);
|
||||||
}
|
}
|
||||||
|
|
||||||
//Either way, we have now determined whether the block was sharable. So it's not *potentially* sharable.
|
//Either way, we have now determined whether the block was sharable. So it's not *potentially* sharable.
|
||||||
m_vecBlockIsPotentiallyHomogenous[i] = false;
|
m_vecBlockIsPotentiallyHomogenous[m_uCurrentBlockForTidying] = false;
|
||||||
|
|
||||||
|
//We've processed a block. This is inside the 'if' because the path outside the 'if' is trivially fast.
|
||||||
|
++m_uNoOfProcessedBlocks;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//Increment the current block, looping around if necessary
|
||||||
|
++m_uCurrentBlockForTidying;
|
||||||
|
m_uCurrentBlockForTidying %= m_uNoOfBlocksInVolume;
|
||||||
}
|
}
|
||||||
|
|
||||||
//FIXME - Better way to do this? Maybe using for_each()?
|
//Identify and remove any homogeneous blocks which are not actually in use.
|
||||||
std::list< std::map<VoxelType, POLYVOX_SHARED_PTR< BlockData<VoxelType> > >::iterator > itersToDelete;
|
std::map<VoxelType, POLYVOX_SHARED_PTR< BlockData<VoxelType> > >::iterator iter = m_pHomogenousBlockData.begin();
|
||||||
for(std::map<VoxelType, POLYVOX_SHARED_PTR< BlockData<VoxelType> > >::iterator iter = m_pHomogenousBlockData.begin(); iter != m_pHomogenousBlockData.end(); ++iter)
|
while(iter != m_pHomogenousBlockData.end())
|
||||||
{
|
{
|
||||||
if(iter->second.unique())
|
if(iter->second.unique())
|
||||||
{
|
{
|
||||||
itersToDelete.push_back(iter);
|
m_pHomogenousBlockData.erase(iter++); //Increments the iterator and returns the previous position to be erased.
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
++iter; //Just increments the iterator.
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
for(std::list< std::map<VoxelType, POLYVOX_SHARED_PTR< BlockData<VoxelType> > >::iterator >::iterator listIter = itersToDelete.begin(); listIter != itersToDelete.end(); ++listIter)
|
|
||||||
{
|
|
||||||
m_pHomogenousBlockData.erase(*listIter);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user