1. Volumes of Fun
  2. Main
  3. PolyVox

Commits

David Williams  committed 6bc379f

More work combining WrapMode and BoundsCheck

  • Participants
  • Parent commits 2b03e84
  • Branches develop

Comments (0)

Files changed (4)

File library/PolyVoxCore/include/PolyVoxCore/BaseVolume.h

View file
  • Ignore whitespace
 	{
 		enum WrapMode
 		{
-			Clamp = 0,
-			Border = 1
+			None = 0,
+			Clamp = 1,
+			Border = 2,
+			DontCheck = 3
 		};
 	}
 	typedef WrapModes::WrapMode WrapMode;
 
+	// Required for a trick to implement specialization of template member
+	// functions in template classes. See http://stackoverflow.com/a/4951057
+	template <WrapMode W> struct WrapModeType{};
+
 	template <typename _VoxelType>
 	class BaseVolume
 	{

File library/PolyVoxCore/include/PolyVoxCore/LowPassFilter.inl

View file
  • Ignore whitespace
 			{
 				for(int32_t x = satLowerCorner.getX(); x <= satUpperCorner.getX(); x++)
 				{
-					AccumulationType previousSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y-1,z, BoundsChecks::BorderPos));
-					AccumulationType currentSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y,z, BoundsChecks::BorderPos));
+					AccumulationType previousSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y-1,z, WrapModes::Border));
+					AccumulationType currentSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y,z, WrapModes::Border));
 
 					satVolume.setVoxelAt(x,y,z,previousSum + currentSum);
 				}
 			{
 				for(int32_t x = satLowerCorner.getX(); x <= satUpperCorner.getX(); x++)
 				{
-					AccumulationType previousSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y,z-1, BoundsChecks::BorderPos));
-					AccumulationType currentSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y,z, BoundsChecks::BorderPos));
+					AccumulationType previousSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y,z-1, WrapModes::Border));
+					AccumulationType currentSum = static_cast<AccumulationType>(satVolume.getVoxel(x,y,z, WrapModes::Border));
 
 					satVolume.setVoxelAt(x,y,z,previousSum + currentSum);
 				}
 					int32_t satUpperY = iSrcY + border;
 					int32_t satUpperZ = iSrcZ + border;
 
-					AccumulationType a = satVolume.getVoxel(satLowerX,satLowerY,satLowerZ, BoundsChecks::BorderPos);
-					AccumulationType b = satVolume.getVoxel(satUpperX,satLowerY,satLowerZ, BoundsChecks::BorderPos);
-					AccumulationType c = satVolume.getVoxel(satLowerX,satUpperY,satLowerZ, BoundsChecks::BorderPos);
-					AccumulationType d = satVolume.getVoxel(satUpperX,satUpperY,satLowerZ, BoundsChecks::BorderPos);
-					AccumulationType e = satVolume.getVoxel(satLowerX,satLowerY,satUpperZ, BoundsChecks::BorderPos);
-					AccumulationType f = satVolume.getVoxel(satUpperX,satLowerY,satUpperZ, BoundsChecks::BorderPos);
-					AccumulationType g = satVolume.getVoxel(satLowerX,satUpperY,satUpperZ, BoundsChecks::BorderPos);
-					AccumulationType h = satVolume.getVoxel(satUpperX,satUpperY,satUpperZ, BoundsChecks::BorderPos);
+					AccumulationType a = satVolume.getVoxel(satLowerX,satLowerY,satLowerZ, WrapModes::Border);
+					AccumulationType b = satVolume.getVoxel(satUpperX,satLowerY,satLowerZ, WrapModes::Border);
+					AccumulationType c = satVolume.getVoxel(satLowerX,satUpperY,satLowerZ, WrapModes::Border);
+					AccumulationType d = satVolume.getVoxel(satUpperX,satUpperY,satLowerZ, WrapModes::Border);
+					AccumulationType e = satVolume.getVoxel(satLowerX,satLowerY,satUpperZ, WrapModes::Border);
+					AccumulationType f = satVolume.getVoxel(satUpperX,satLowerY,satUpperZ, WrapModes::Border);
+					AccumulationType g = satVolume.getVoxel(satLowerX,satUpperY,satUpperZ, WrapModes::Border);
+					AccumulationType h = satVolume.getVoxel(satUpperX,satUpperY,satUpperZ, WrapModes::Border);
 
 					AccumulationType sum = h+c-d-g-f-a+b+e;
 					uint32_t sideLength = border * 2 + 1;

File library/PolyVoxCore/include/PolyVoxCore/RawVolume.h

View file
  • Ignore whitespace
 		~RawVolume();
 
 		/// Gets a voxel at the position given by <tt>x,y,z</tt> coordinates
-		template <BoundsCheck eBoundsCheck>
+		template <WrapMode eWrapMode>
 		VoxelType getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder = VoxelType()) const;
 
 		/// Gets a voxel at the position given by <tt>x,y,z</tt> coordinates
-		VoxelType getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, BoundsCheck eBoundsCheck = BoundsChecks::Full, VoxelType tBorder = VoxelType()) const;
+		VoxelType getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, WrapMode eWrapMode = WrapModes::None, VoxelType tBorder = VoxelType()) const;
 		/// Gets a voxel at the position given by a 3D vector
-		VoxelType getVoxel(const Vector3DInt32& v3dPos, BoundsCheck eBoundsCheck = BoundsChecks::Full, VoxelType tBorder = VoxelType()) const;
+		VoxelType getVoxel(const Vector3DInt32& v3dPos, WrapMode eWrapMode = WrapModes::None, VoxelType tBorder = VoxelType()) const;
 		/// Gets a voxel at the position given by <tt>x,y,z</tt> coordinates
 		VoxelType getVoxelAt(int32_t uXPos, int32_t uYPos, int32_t uZPos) const;
 		/// Gets a voxel at the position given by a 3D vector
 		VoxelType getVoxelAt(const Vector3DInt32& v3dPos) const;
 		/// Gets a voxel at the position given by <tt>x,y,z</tt> coordinates
-		VoxelType getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, WrapMode eWrapMode, VoxelType tBorder = VoxelType()) const;
+		//VoxelType getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, WrapMode eWrapMode, VoxelType tBorder = VoxelType()) const;
 		/// Gets a voxel at the position given by a 3D vector
-		VoxelType getVoxel(const Vector3DInt32& v3dPos, WrapMode eWrapMode, VoxelType tBorder = VoxelType()) const;
+		//VoxelType getVoxel(const Vector3DInt32& v3dPos, WrapMode eWrapMode, VoxelType tBorder = VoxelType()) const;
 
 		/// Sets the voxel at the position given by <tt>x,y,z</tt> coordinates
 		void setVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tValue, BoundsCheck eBoundsCheck = BoundsChecks::Full);
 	private:
 		void initialise(const Region& regValidRegion);
 
-		template <BoundsCheck eBoundsCheck>
-		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<eBoundsCheck>) const;
-		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::Full>) const;
-		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::None>) const;
-		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::ClampPos>) const;
-		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::BorderPos>) const;
+		template <WrapMode eWrapMode>
+		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<eWrapMode>) const;
+		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::None>) const;
+		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::Clamp>) const;
+		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::Border>) const;
+		VoxelType getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::DontCheck>) const;
 
 		//The block data
 		VoxelType* m_pData;

File library/PolyVoxCore/include/PolyVoxCore/RawVolume.inl

View file
  • Ignore whitespace
 	/// \return The voxel value
 	////////////////////////////////////////////////////////////////////////////////
 	template <typename VoxelType>
-	template <BoundsCheck eBoundsCheck>
+	template <WrapMode eWrapMode>
 	VoxelType RawVolume<VoxelType>::getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder) const
 	{
 		// Simply call through to the real implementation
-		return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<eBoundsCheck>());
+		return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<eWrapMode>());
 	}
 
 	////////////////////////////////////////////////////////////////////////////////
 	/// \return The voxel value
 	////////////////////////////////////////////////////////////////////////////////
 	template <typename VoxelType>
-	VoxelType RawVolume<VoxelType>::getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, BoundsCheck eBoundsCheck, VoxelType tBorder) const
+	VoxelType RawVolume<VoxelType>::getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, WrapMode eWrapMode, VoxelType tBorder) const
 	{
 		// If bounds checking is enabled then we validate the
 		// bounds, and throw an exception if they are violated.
-		if(eBoundsCheck == BoundsChecks::Full)
+		if(eWrapMode == WrapModes::None)
 		{
 			// Call through to the real implementation
-			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<BoundsChecks::Full>());
+			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<WrapModes::None>());
 		}
-		else if(eBoundsCheck == BoundsChecks::None)
+		else if(eWrapMode == WrapModes::Clamp)
 		{
 			// Call through to the real implementation
-			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<BoundsChecks::None>());
+			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<WrapModes::Clamp>());
 		}
-		else if(eBoundsCheck == BoundsChecks::ClampPos)
+		else if(eWrapMode == WrapModes::Border)
 		{
 			// Call through to the real implementation
-			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<BoundsChecks::ClampPos>());
+			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<WrapModes::Border>());
 		}
 		else
 		{
 			// Call through to the real implementation
-			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<BoundsChecks::BorderPos>());
+			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<WrapModes::DontCheck>());
 		}
 	}
 
 	/// is inside the volume's enclosing region then you can skip this check to gain some performance.
 	////////////////////////////////////////////////////////////////////////////////
 	template <typename VoxelType>
-	VoxelType RawVolume<VoxelType>::getVoxel(const Vector3DInt32& v3dPos, BoundsCheck eBoundsCheck, VoxelType tBorder) const
+	VoxelType RawVolume<VoxelType>::getVoxel(const Vector3DInt32& v3dPos, WrapMode eWrapMode, VoxelType tBorder) const
 	{
-		return getVoxel(v3dPos.getX(), v3dPos.getY(), v3dPos.getZ(), eBoundsCheck, tBorder);
+		return getVoxel(v3dPos.getX(), v3dPos.getY(), v3dPos.getZ(), eWrapMode, tBorder);
 	}
 
 	////////////////////////////////////////////////////////////////////////////////
 	/// \param uZPos The \c z position of the voxel
 	/// \return The voxel value
 	////////////////////////////////////////////////////////////////////////////////
-	template <typename VoxelType>
+	/*template <typename VoxelType>
 	VoxelType RawVolume<VoxelType>::getVoxel(int32_t uXPos, int32_t uYPos, int32_t uZPos, WrapMode eWrapMode, VoxelType tBorder) const
 	{
 		switch(eWrapMode)
 	VoxelType RawVolume<VoxelType>::getVoxel(const Vector3DInt32& v3dPos, WrapMode eWrapMode, VoxelType tBorder) const
 	{
 		return getVoxel(v3dPos.getX(), v3dPos.getY(), v3dPos.getZ(), eWrapMode, tBorder);
-	}
+	}*/
 
 	////////////////////////////////////////////////////////////////////////////////
 	/// \param uXPos the \c x position of the voxel
 	}
 
 	template <typename VoxelType>
-	template <BoundsCheck eBoundsCheck>
-	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<eBoundsCheck>) const
+	template <WrapMode eWrapMode>
+	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<eWrapMode>) const
 	{
 		POLYVOX_THROW(not_implemented, "This function is not implemented and should never be called!");
 	}
 
 	template <typename VoxelType>
-	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::Full>) const
+	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::None>) const
 	{
 		if(this->m_regValidRegion.containsPoint(Vector3DInt32(uXPos, uYPos, uZPos)) == false)
 		{
 			POLYVOX_THROW(std::out_of_range, "Position is outside valid region");
 		}
 
-		return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<BoundsChecks::None>());
-	}
-
-	template <typename VoxelType>
-	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::None>) const
-	{
-		const Vector3DInt32& v3dLowerCorner = this->m_regValidRegion.getLowerCorner();
-		int32_t iLocalXPos = uXPos - v3dLowerCorner.getX();
-		int32_t iLocalYPos = uYPos - v3dLowerCorner.getY();
-		int32_t iLocalZPos = uZPos - v3dLowerCorner.getZ();
-
-		return m_pData
-		[
-			iLocalXPos + 
-			iLocalYPos * this->getWidth() + 
-			iLocalZPos * this->getWidth() * this->getHeight()
-		];
+		return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<WrapModes::DontCheck>());
 	}
 
 	template <typename VoxelType>
-	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::ClampPos>) const
+	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::Clamp>) const
 	{
 		//Perform clamping
 		uXPos = (std::max)(uXPos, this->m_regValidRegion.getLowerX());
 		uYPos = (std::min)(uYPos, this->m_regValidRegion.getUpperY());
 		uZPos = (std::min)(uZPos, this->m_regValidRegion.getUpperZ());
 
-		return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<BoundsChecks::None>());
+		return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<WrapModes::DontCheck>());
 	}
 
 	template <typename VoxelType>
-	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, BoundsCheckType<BoundsChecks::BorderPos>) const
+	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::Border>) const
 	{
 		if(this->m_regValidRegion.containsPoint(uXPos, uYPos, uZPos))
 		{
-			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, BoundsCheckType<BoundsChecks::None>()); // No bounds checks as we've just validated the position.
+			return getVoxelImpl(uXPos, uYPos, uZPos, tBorder, WrapModeType<WrapModes::DontCheck>()); // No bounds checks as we've just validated the position.
 		}
 		else
 		{
 			return tBorder; //FIXME - Should return border value.
 		}
 	}
+
+	template <typename VoxelType>
+	VoxelType RawVolume<VoxelType>::getVoxelImpl(int32_t uXPos, int32_t uYPos, int32_t uZPos, VoxelType tBorder, WrapModeType<WrapModes::DontCheck>) const
+	{
+		const Vector3DInt32& v3dLowerCorner = this->m_regValidRegion.getLowerCorner();
+		int32_t iLocalXPos = uXPos - v3dLowerCorner.getX();
+		int32_t iLocalYPos = uYPos - v3dLowerCorner.getY();
+		int32_t iLocalZPos = uZPos - v3dLowerCorner.getZ();
+
+		return m_pData
+		[
+			iLocalXPos + 
+			iLocalYPos * this->getWidth() + 
+			iLocalZPos * this->getWidth() * this->getHeight()
+		];
+	}
 }