Procházet zdrojové kódy

Work on DX11 textures and HardwarePixelBuffer.
Doesn't compile but commiting before i delete DX11 HardwarePixelBuffer just in case I need it later

Marko Pintera před 13 roky
rodič
revize
c2cba92975
27 změnil soubory, kde provedl 2475 přidání a 844 odebrání
  1. 6 0
      CamelotD3D11RenderSystem/CamelotD3D11RenderSystem.vcxproj
  2. 18 0
      CamelotD3D11RenderSystem/CamelotD3D11RenderSystem.vcxproj.filters
  3. 86 0
      CamelotD3D11RenderSystem/Include/CmD3D11HardwarePixelBuffer.h
  4. 4 1
      CamelotD3D11RenderSystem/Include/CmD3D11Mappings.h
  5. 23 0
      CamelotD3D11RenderSystem/Include/CmD3D11RenderTexture.h
  6. 81 0
      CamelotD3D11RenderSystem/Include/CmD3D11Texture.h
  7. 4 4
      CamelotD3D11RenderSystem/Source/CmD3D11HardwareBuffer.cpp
  8. 765 0
      CamelotD3D11RenderSystem/Source/CmD3D11HardwarePixelBuffer.cpp
  9. 42 3
      CamelotD3D11RenderSystem/Source/CmD3D11Mappings.cpp
  10. 6 0
      CamelotD3D11RenderSystem/Source/CmD3D11RenderTexture.cpp
  11. 732 732
      CamelotD3D11RenderSystem/Source/CmD3D11RenderWindow.cpp
  12. 584 0
      CamelotD3D11RenderSystem/Source/CmD3D11Texture.cpp
  13. 52 53
      CamelotD3D9Renderer/Include/CmD3D9HardwarePixelBuffer.h
  14. 3 3
      CamelotD3D9Renderer/Source/CmD3D9HardwareIndexBuffer.cpp
  15. 1 1
      CamelotD3D9Renderer/Source/CmD3D9HardwarePixelBuffer.cpp
  16. 3 3
      CamelotD3D9Renderer/Source/CmD3D9HardwareVertexBuffer.cpp
  17. 14 0
      CamelotGLRenderer/Include/CmGLDepthStencilBuffer.h
  18. 2 2
      CamelotGLRenderer/Source/CmGLHardwareIndexBuffer.cpp
  19. 2 2
      CamelotGLRenderer/Source/CmGLHardwareVertexBuffer.cpp
  20. 21 0
      CamelotRenderer/Include/CmCommon.h
  21. 1 18
      CamelotRenderer/Include/CmHardwareBuffer.h
  22. 0 1
      CamelotRenderer/Include/CmHardwarePixelBuffer.h
  23. 7 17
      CamelotRenderer/Include/CmTexture.h
  24. 2 2
      CamelotRenderer/Source/CmHardwarePixelBuffer.cpp
  25. 1 1
      CamelotRenderer/Source/CmTexture.cpp
  26. 13 1
      CamelotRenderer/TODO.txt
  27. 2 0
      CamelotUtility/Include/CmPixelData.h

+ 6 - 0
CamelotD3D11RenderSystem/CamelotD3D11RenderSystem.vcxproj

@@ -154,13 +154,16 @@
     <ClInclude Include="Include\CmD3D11GpuProgram.h" />
     <ClInclude Include="Include\CmD3D11GpuProgramManager.h" />
     <ClInclude Include="Include\CmD3D11HardwareBuffer.h" />
+    <ClInclude Include="Include\CmD3D11HardwarePixelBuffer.h" />
     <ClInclude Include="Include\CmD3D11HLSLProgram.h" />
     <ClInclude Include="Include\CmD3D11HardwareIndexBuffer.h" />
     <ClInclude Include="Include\CmD3D11Mappings.h" />
     <ClInclude Include="Include\CmD3D11Prerequisites.h" />
     <ClInclude Include="Include\CmD3D11HardwareVertexBuffer.h" />
     <ClInclude Include="Include\CmD3D11RenderSystem.h" />
+    <ClInclude Include="Include\CmD3D11RenderTexture.h" />
     <ClInclude Include="Include\CmD3D11RenderWindow.h" />
+    <ClInclude Include="Include\CmD3D11Texture.h" />
     <ClInclude Include="Include\CmD3D11VertexDeclaration.h" />
     <ClInclude Include="Include\CmD3D11VideoMode.h" />
     <ClInclude Include="Include\CmD3D11VideoModeList.h" />
@@ -174,12 +177,15 @@
     <ClCompile Include="Source\CmD3D11HardwareBuffer.cpp" />
     <ClCompile Include="Source\CmD3D11HardwareBufferManager.cpp" />
     <ClCompile Include="Source\CmD3D11HardwareConstantBuffer.cpp" />
+    <ClCompile Include="Source\CmD3D11HardwarePixelBuffer.cpp" />
     <ClCompile Include="Source\CmD3D11HLSLProgram.cpp" />
     <ClCompile Include="Source\CmD3D11HardwareIndexBuffer.cpp" />
     <ClCompile Include="Source\CmD3D11Mappings.cpp" />
     <ClCompile Include="Source\CmD3D11HardwareVertexBuffer.cpp" />
     <ClCompile Include="Source\CmD3D11RenderSystem.cpp" />
+    <ClCompile Include="Source\CmD3D11RenderTexture.cpp" />
     <ClCompile Include="Source\CmD3D11RenderWindow.cpp" />
+    <ClCompile Include="Source\CmD3D11Texture.cpp" />
     <ClCompile Include="Source\CmD3D11VertexDeclaration.cpp" />
     <ClCompile Include="Source\CmD3D11VideoMode.cpp" />
     <ClCompile Include="Source\CmD3D11VideoModeList.cpp" />

+ 18 - 0
CamelotD3D11RenderSystem/CamelotD3D11RenderSystem.vcxproj.filters

@@ -69,6 +69,15 @@
     <ClInclude Include="Include\CmD3D11RenderWindow.h">
       <Filter>Header Files</Filter>
     </ClInclude>
+    <ClInclude Include="Include\CmD3D11HardwarePixelBuffer.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="Include\CmD3D11Texture.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="Include\CmD3D11RenderTexture.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="Source\CmD3D11GpuProgram.cpp">
@@ -122,5 +131,14 @@
     <ClCompile Include="Source\CmD3D11RenderWindow.cpp">
       <Filter>Source Files</Filter>
     </ClCompile>
+    <ClCompile Include="Source\CmD3D11HardwarePixelBuffer.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="Source\CmD3D11Texture.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="Source\CmD3D11RenderTexture.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
   </ItemGroup>
 </Project>

+ 86 - 0
CamelotD3D11RenderSystem/Include/CmD3D11HardwarePixelBuffer.h

@@ -0,0 +1,86 @@
+#pragma once
+
+#include "CmD3D11Prerequisites.h"
+#include "CmHardwarePixelBuffer.h"
+
+namespace CamelotEngine
+{
+	class CM_D3D11_EXPORT D3D11HardwarePixelBuffer : public HardwarePixelBuffer
+	{
+	public:
+		D3D11HardwarePixelBuffer(D3D11Texture* parentTexture, D3D11Device& device, UINT32 subresourceIndex,
+			UINT32 width, UINT32 height, UINT32 depth, UINT32 face, PixelFormat format, HardwareBuffer::Usage usage);
+
+		/// @copydoc HardwarePixelBuffer::blit
+		void blit(const HardwarePixelBufferPtr& src, const Box& srcBox, const Box& dstBox);
+
+		/// @copydoc HardwarePixelBuffer::blitFromMemory
+		void blitFromMemory(const PixelData& src, const Box& dstBox);
+
+		/// @copydoc HardwarePixelBuffer::blitToMemory
+		void blitToMemory(const Box& srcBox, const PixelData& dst);
+
+		/// Internal function to update mipmaps on update of level 0
+		void _genMipmaps();
+
+		~D3D11HardwarePixelBuffer();
+
+		/// Get rendertarget for z slice
+		RenderTexture *getRenderTarget(UINT32 zoffset);
+
+		/// Notify TextureBuffer of destruction of render target
+		virtual void _clearSliceRTT(UINT32 zoffset)
+		{
+			if (mSliceTRT.size() > zoffset)
+			{
+				mSliceTRT[zoffset] = 0;
+			}
+		}
+
+		D3D11Texture * getParentTexture() const;
+		UINT32 getSubresourceIndex() const;
+		UINT32 getFace() const;
+
+	protected:
+		/// Lock a box
+		PixelData lockImpl(const Box lockBox, LockOptions options);
+
+		/// Unlock a box
+		void unlockImpl(void);
+
+		/// D3DDevice pointer
+		D3D11Device& mDevice;
+
+		D3D11Texture* mParentTexture;
+		UINT32 mSubresourceIndex;
+
+		// if the usage is static - alloc at lock then use device UpdateSubresource when unlock and free memory
+		UINT8* mDataForStaticUsageLock; 
+
+		UINT32 mFace;
+
+		Box mLockBox;
+		PixelData mCurrentLock;
+		LockOptions mCurrentLockOptions;
+
+		D3D11_BOX convertBoxToDx11Box(const Box &inBox) const;
+
+		/// Util functions to convert a D3D locked box to a pixel box
+		void fromD3DLock(PixelData &rval, const DXGI_MAPPED_RECT &lrect);
+
+		/// Render targets
+		typedef vector<RenderTexture*>::type SliceTRT;
+		SliceTRT mSliceTRT;
+
+		void createStagingBuffer();
+		bool mUsingStagingBuffer;
+		ID3D11Resource *mStagingBuffer;
+
+		void* _map(ID3D11Resource *res, D3D11_MAP flags);
+		void* _mapstagingbuffer(D3D11_MAP flags);
+		void* _mapstaticbuffer(PixelData lock);
+		void _unmap(ID3D11Resource *res);
+		void _unmapstagingbuffer(bool copyback = true);
+		void _unmapstaticbuffer();
+	};
+}

+ 4 - 1
CamelotD3D11RenderSystem/Include/CmD3D11Mappings.h

@@ -56,6 +56,7 @@ namespace CamelotEngine
 		static void get(const Color& inColour, float * outColour );
 		static bool isMappingWrite(D3D11_MAP map);
 		static bool isMappingRead(D3D11_MAP map);
+		static D3D11_BOX toDx11Box(const Box &inBox);
 
 		/// utility method, convert D3D11 pixel format to Ogre pixel format
 		static PixelFormat _getPF(DXGI_FORMAT d3dPF);
@@ -75,9 +76,11 @@ namespace CamelotEngine
 
 		static TextureType _getTexType(D3D11_SRV_DIMENSION type);
 
-		static size_t _getSizeInBytes(PixelFormat pf, size_t xcount = 1, size_t ycount = 1);
+		static UINT32 _getSizeInBytes(PixelFormat pf, UINT32 xcount = 1, UINT32 ycount = 1);
 
 		static UINT _getTextureBindFlags(DXGI_FORMAT format, bool isdynamic);
 		static UINT _getTextureMiscFlags(UINT bindflags, TextureType textype, bool isdynamic);
+
+		static D3D11_MAP _getLockOptions(LockOptions lockOptions);
 	};
 }

+ 23 - 0
CamelotD3D11RenderSystem/Include/CmD3D11RenderTexture.h

@@ -0,0 +1,23 @@
+#pragma once
+
+#include "CmD3D11Prerequisites.h"
+#include "CmRenderTexture.h"
+
+namespace CamelotEngine
+{
+	class D3D11RenderTexture : public RenderTexture
+	{
+		D3D11Device& mDevice;
+		ID3D11RenderTargetView* mRenderTargetView;
+		ID3D11DepthStencilView* mDepthStencilView;
+	public:
+		D3D11RenderTexture(const String &name, D3D11HardwarePixelBuffer *buffer, D3D11Device& device);
+		virtual ~D3D11RenderTexture();
+
+		void rebind(D3D11HardwarePixelBuffer *buffer);
+
+		virtual void getCustomAttribute(const String& name, void *pData);
+
+		bool requiresTextureFlipping() const { return false; }
+	};
+}

+ 81 - 0
CamelotD3D11RenderSystem/Include/CmD3D11Texture.h

@@ -0,0 +1,81 @@
+#pragma once
+
+#include "CmD3D11Prerequisites.h"
+#include "CmTexture.h"
+
+namespace CamelotEngine
+{
+	class D3D11Texture : public Texture
+	{
+	public:
+		~D3D11Texture();
+
+		/**
+		 * @copydoc Texture::setRawPixels_internal
+		 */
+		void setRawPixels_internal(const PixelData& data, UINT32 face = 0, UINT32 mip = 0);
+
+		/**
+		 * @copydoc Texture::getRawPixels_internal
+		 */
+		void getRawPixels_internal(UINT32 face, UINT32 mip, AsyncOp& op);
+
+		/**
+		 * @copydoc Texture::copy_internal
+		 */
+		void copy_internal(TexturePtr& target);
+
+		PixelData lock(LockOptions options, UINT32 mipLevel = 0, UINT32 face = 0);
+		void unlock();
+
+		ID3D11Resource* getDX11Resource() const { return mTex; }
+	protected:
+		D3D11Texture();
+
+		ID3D11Texture1D* m1DTex;
+		ID3D11Texture2D* m2DTex;
+		ID3D11Texture3D* m3DTex;	
+		ID3D11Resource* mTex;		
+
+		ID3D11ShaderResourceView* mShaderResourceView;
+		D3D11_SHADER_RESOURCE_VIEW_DESC mSRVDesc;
+
+		ID3D11Resource* mStagingBuffer;
+		PixelData* mStaticBuffer;
+		UINT32 mLockedSubresourceIdx;
+		bool mLockedForReading;
+
+		/// internal method, create a blank normal 1D Dtexture
+		void _create1DTex();
+		/// internal method, create a blank normal 2D texture
+		void _create2DTex();
+		/// internal method, create a blank cube texture
+		void _create3DTex();
+
+		void _createStagingBuffer();
+
+		void* _map(ID3D11Resource* res, D3D11_MAP flags, UINT32 mipLevel, UINT32 face);
+		void _unmap(ID3D11Resource* res);
+
+		void* _mapstagingbuffer(D3D11_MAP flags, UINT32 mipLevel, UINT32 face);
+		void _unmapstagingbuffer();
+		
+		void* _mapstaticbuffer(PixelData lock, UINT32 mipLevel, UINT32 slice);
+		void _unmapstaticbuffer();
+
+		/**
+		 * @brief	Resource::initialize_internal
+		 */
+		void initialize_internal();
+
+		/**
+		 * @copydoc Texture::createInternalResourcesImpl
+		 */
+		void createInternalResourcesImpl();
+		
+		/**
+		 * @copydoc Texture::freeInternalResourcesImpl
+		 */
+		void freeInternalResourcesImpl();
+	};
+}

+ 4 - 4
CamelotD3D11RenderSystem/Source/CmD3D11HardwareBuffer.cpp

@@ -72,7 +72,7 @@ namespace CamelotEngine
 
 			switch(options)
 			{
-			case HBL_DISCARD:
+			case HBL_WRITE_ONLY_DISCARD:
 				if (mUsage & HardwareBuffer::HBU_DYNAMIC)
 				{
 					// Map cannot be called with MAP_WRITE access, 
@@ -92,7 +92,7 @@ namespace CamelotEngine
 					LOGWRN("DISCARD lock is only available on dynamic buffers. Falling back to normal write.");
 				}
 				break;
-			case HBL_NO_OVERWRITE:
+			case HBL_WRITE_ONLY_NO_OVERWRITE:
 				if(mBufferType == INDEX_BUFFER || mBufferType == VERTEX_BUFFER)
 					mapType = D3D11_MAP_WRITE_NO_OVERWRITE;
 				else
@@ -102,7 +102,7 @@ namespace CamelotEngine
 					LOGWRN("NO_OVERWRITE lock is not available on this (" + toString(mBufferType) + ") buffer type. Falling back to normal write.");
 				}
 				break;
-			case HBL_NORMAL:
+			case HBL_READ_WRITE:
 				if ((mDesc.CPUAccessFlags & D3D11_CPU_ACCESS_READ) != 0 &&
 					(mDesc.CPUAccessFlags & D3D11_CPU_ACCESS_WRITE) != 0)
 				{
@@ -154,7 +154,7 @@ namespace CamelotEngine
 			}
 
 			// schedule a copy to the staging
-			if (options != HBL_DISCARD)
+			if (options != HBL_WRITE_ONLY_DISCARD)
 				mpTempStagingBuffer->copyData(*this, 0, 0, mSizeInBytes, true);
 
 			// register whether we'll need to upload on unlock

+ 765 - 0
CamelotD3D11RenderSystem/Source/CmD3D11HardwarePixelBuffer.cpp

@@ -0,0 +1,765 @@
+#include "CmD3D11HardwarePixelBuffer.h"
+#include "CmD3D11Device.h"
+#include "CmD3D11Mappings.h"
+#include "CmRenderSystem.h"
+#include "CmTexture.h"
+#include "CmDataStream.h"
+
+namespace CamelotEngine
+{
+	D3D11HardwarePixelBuffer::D3D11HardwarePixelBuffer(D3D11Texture* parentTexture, D3D11Device& device, UINT32 subresourceIndex,
+		UINT32 width, UINT32 height, UINT32 depth, UINT32 face, PixelFormat format, HardwareBuffer::Usage usage):
+	HardwarePixelBuffer(width, height, depth, format, usage, false),
+		mParentTexture(parentTexture),
+		mDevice(device),
+		mSubresourceIndex(subresourceIndex),
+		mFace(face),
+		mDataForStaticUsageLock(0),
+		mStagingBuffer(NULL)
+	{
+		if(mUsage & TU_RENDERTARGET)
+		{
+			// Create render target for each slice
+			mSliceTRT.reserve(mDepth);
+			for(UINT32 zoffset = 0; zoffset < mDepth; ++zoffset)
+			{
+				String name;
+				name = "rtt/" + toString((UINT32)mParentTexture) + "/" + toString(mSubresourceIndex);
+
+				RenderTexture *trt = new D3D11RenderTexture(name, this, mDevice);
+				mSliceTRT.push_back(trt);
+				
+				RenderSystem::instance().attachRenderTarget(*trt);
+			}
+		}
+	}
+
+	D3D11HardwarePixelBuffer::~D3D11HardwarePixelBuffer()
+	{
+		if(!mSliceTRT.empty())
+		{	
+			// Delete all render targets that are not yet deleted via _clearSliceRTT
+			for(UINT32 zoffset = 0; zoffset < mDepth; ++zoffset)
+			{
+				if(mSliceTRT[zoffset])
+					RenderSystem::instance().destroyRenderTarget(mSliceTRT[zoffset]);
+			}
+		}
+
+		SAFE_DELETE_ARRAY(mDataForStaticUsageLock);
+		SAFE_RELEASE(mStagingBuffer);
+	}
+  
+	// Util functions to convert a D3D locked box to a pixel box
+	void D3D11HardwarePixelBuffer::fromD3DLock(PixelData& rval, const DXGI_MAPPED_RECT& lrect)
+	{
+		rval.rowPitch = lrect.Pitch / PixelUtil::getNumElemBytes(rval.format);
+		rval.slicePitch = rval.rowPitch * rval.getHeight();
+		assert((lrect.Pitch % PixelUtil::getNumElemBytes(rval.format))==0);
+		rval.data = lrect.pBits;
+	}
+
+	void* D3D11HardwarePixelBuffer::_map(ID3D11Resource *res, D3D11_MAP flags)
+	{
+		D3D11_MAPPED_SUBRESOURCE pMappedResource;
+		pMappedResource.pData = NULL;
+
+		switch(mParentTexture->getTextureType()) 
+		{
+		case TEX_TYPE_1D:
+			{  
+				mDevice.getImmediateContext()->Map(res, static_cast<UINT>(mSubresourceIndex), flags, 0, &pMappedResource);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 1D texture\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_CUBE_MAP:
+		case TEX_TYPE_2D:
+			{
+				mDevice.getImmediateContext()->Map(res, D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mFace, mParentTexture->getNumMipmaps()+1), 
+					flags, 0, &pMappedResource);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 2D texture\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_2D_ARRAY:
+			{
+				mDevice.getImmediateContext()->Map(res, D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mLockBox.front, mParentTexture->getNumMipmaps()+1), 
+					flags, 0, &pMappedResource);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 2D texture array\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_3D:
+			{
+				mDevice.getImmediateContext()->Map(res, static_cast<UINT>(mSubresourceIndex), flags, 0, &pMappedResource);
+
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 3D texture\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		}
+
+		return pMappedResource.pData;
+	}
+
+	void *D3D11HardwarePixelBuffer::_mapstaticbuffer(PixelData lock)
+	{
+		// for static usage just alloc
+		size_t sizeOfImage = lock.getConsecutiveSize();
+		
+		mDataForStaticUsageLock = new UINT8[sizeOfImage];
+		return mDataForStaticUsageLock;
+	}
+  
+	void *D3D11HardwarePixelBuffer::_mapstagingbuffer(D3D11_MAP flags)
+	{
+		if(!mStagingBuffer)
+			createStagingBuffer();
+
+		if(flags == D3D11_MAP_READ_WRITE || flags == D3D11_MAP_READ || flags == D3D11_MAP_WRITE)  
+		{
+			if(mLockBox.getHeight() == mParentTexture->getHeight() && mLockBox.getWidth() == mParentTexture->getWidth())
+				mDevice.getImmediateContext()->CopyResource(mStagingBuffer, mParentTexture->getTextureResource());
+			else
+			{
+				D3D11_BOX dstBoxDx11 = convertBoxToDx11Box(mLockBox);
+				dstBoxDx11.front = 0;
+				dstBoxDx11.back = mLockBox.getDepth();
+
+				unsigned int subresource = D3D11CalcSubresource(mSubresourceIndex, mLockBox.front, mParentTexture->getNumMipmaps()+1);
+				mDevice.getImmediateContext()->CopySubresourceRegion(mStagingBuffer, subresource, mLockBox.left, mLockBox.top, 
+					mSubresourceIndex, mParentTexture->getTextureResource(), subresource, &dstBoxDx11);
+			}
+		}
+		else if(flags == D3D11_MAP_WRITE_DISCARD)
+			flags = D3D11_MAP_WRITE; // stagingbuffer doesn't support discarding
+
+		return _map(mStagingBuffer, flags);
+	}
+ 
+	PixelData D3D11HardwarePixelBuffer::lockImpl(const Box lockBox, LockOptions options)
+	{
+		// Check for misuse
+		if(mUsage & TU_RENDERTARGET)
+			CM_EXCEPT(RenderingAPIException, "DirectX does not allow locking of or directly writing to RenderTargets. Use blitFromMemory if you need the contents.");	
+
+		mLockBox = lockBox;
+
+		// Set extents and format
+		// Note that we do not carry over the left/top/front here, since the returned
+		// PixelBox will be re-based from the locking point onwards
+		PixelData rval(lockBox.getWidth(), lockBox.getHeight(), lockBox.getDepth(), mFormat);
+		// Set locking flags according to options
+		D3D11_MAP  flags = D3D11_MAP_WRITE_DISCARD ;
+		switch(options)
+		{
+		case HBL_WRITE_ONLY_NO_OVERWRITE:
+			flags = D3D11_MAP_WRITE_NO_OVERWRITE;
+			break;
+		case HBL_READ_WRITE:
+			flags = D3D11_MAP_READ_WRITE;
+			break;
+		case HBL_WRITE_ONLY_DISCARD:
+			flags = D3D11_MAP_WRITE_DISCARD;
+			break;
+		case HBL_READ_ONLY:
+			flags = D3D11_MAP_READ;
+			break;
+		case HBL_WRITE_ONLY:
+			flags = D3D11_MAP_WRITE;
+			break;
+		default: 
+			break;
+		};
+
+		size_t offset = 0;
+
+		if(mUsage == HBU_STATIC || mUsage & HBU_DYNAMIC)
+		{
+			if(mUsage == HBU_STATIC || options == HBL_READ_ONLY || options == HBL_READ_WRITE || options == HBL_WRITE_ONLY)
+				rval.data = _mapstagingbuffer(flags);
+			else
+				rval.data = _map(mParentTexture->getTextureResource(), flags);
+
+			// calculate the offset in bytes
+			offset = D3D11Mappings::_getSizeInBytes(rval.format, rval.left, rval.front);
+			// add the offset, so the right memory will be changed
+			//rval.data = static_cast<int*>(rval.data) + offset;
+		}
+		else
+		{
+			size_t sizeOfImage = rval.getConsecutiveSize();
+            mDataForStaticUsageLock = new UINT8[sizeOfImage];
+            rval.data = mDataForStaticUsageLock;
+		}
+		// save without offset
+ 		mCurrentLock = rval;
+		mCurrentLockOptions = options;
+
+		// add the offset, so the right memory will be changed
+		rval.data = static_cast<int*>(rval.data) + offset;
+
+		return rval;
+	}
+
+	void D3D11HardwarePixelBuffer::_unmap(ID3D11Resource *res)
+	{
+		switch(mParentTexture->getTextureType()) {
+		case TEX_TYPE_1D:
+			{
+				mDevice.getImmediateContext()->Unmap(res, mSubresourceIndex);
+			}
+			break;
+		case TEX_TYPE_CUBE_MAP:
+		case TEX_TYPE_2D:
+			{							  
+				mDevice.getImmediateContext()->Unmap(res, D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mFace, mParentTexture->getNumMipmaps()+1));
+			}
+			break;
+		case TEX_TYPE_2D_ARRAY:
+			{
+				mDevice.getImmediateContext()->Unmap(res, D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mLockBox.front, mParentTexture->getNumMipmaps()+1));
+			}
+			break;
+		case TEX_TYPE_3D:
+			{
+				mDevice.getImmediateContext()->Unmap(res, mSubresourceIndex);
+			}
+			break;
+		}
+
+		if (mDevice.hasError())
+		{
+			String errorDescription = mDevice.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "D3D11 device unmap resource\nError Description:" + errorDescription);
+		}
+	}
+
+	void D3D11HardwarePixelBuffer::_unmapstaticbuffer()
+	{
+		D3D11_BOX dstBoxDx11 = convertBoxToDx11Box(mLockBox);
+		dstBoxDx11.front = 0;
+		dstBoxDx11.back = mLockBox.getDepth();
+
+		size_t rowWidth = D3D11Mappings::_getSizeInBytes(mCurrentLock.format, mCurrentLock.getWidth());
+
+		switch(mParentTexture->getTextureType()) {
+		case TEX_TYPE_1D:
+			{
+
+				mDevice.getImmediateContext()->UpdateSubresource(mParentTexture->GetTex1D(), 
+					static_cast<UINT>(mSubresourceIndex), &dstBoxDx11, 
+					mDataForStaticUsageLock, rowWidth, 0);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 1D texture\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_CUBE_MAP:
+		case TEX_TYPE_2D:
+			{
+				mDevice.getImmediateContext()->UpdateSubresource(mParentTexture->GetTex2D(), 
+					D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mFace, mParentTexture->getNumMipmaps()+1),
+					&dstBoxDx11, 
+					mDataForStaticUsageLock, rowWidth, 0);
+
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 2D texture\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_2D_ARRAY:
+			{
+				mDevice.getImmediateContext()->UpdateSubresource(mParentTexture->GetTex2D(), 
+					D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mLockBox.front, mParentTexture->getNumMipmaps()+1),
+					&dstBoxDx11, mDataForStaticUsageLock, rowWidth, 0);
+
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 2D texture array\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_3D:
+			{
+				size_t sliceWidth = D3D11Mappings::_getSizeInBytes(mCurrentLock.format, mCurrentLock.getWidth(), mCurrentLock.getHeight());
+
+				mDevice.getImmediateContext()->UpdateSubresource(mParentTexture->GetTex3D(), static_cast<UINT>(mSubresourceIndex), 
+					&dstBoxDx11, mDataForStaticUsageLock, rowWidth, sliceWidth);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map 3D texture\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		}
+
+		SAFE_DELETE_ARRAY(mDataForStaticUsageLock) ;
+	}
+  
+	void D3D11HardwarePixelBuffer::_unmapstagingbuffer(bool copyback)
+	{
+		_unmap(mStagingBuffer);
+
+		if(copyback)
+		{
+			if(mLockBox.getHeight() == mParentTexture->getHeight() && mLockBox.getWidth() == mParentTexture->getWidth())
+				mDevice.getImmediateContext()->CopyResource(mParentTexture->getTextureResource(), mStagingBuffer);
+			else
+			{
+				D3D11_BOX dstBoxDx11 = convertBoxToDx11Box(mLockBox);
+				dstBoxDx11.front = 0;
+				dstBoxDx11.back = mLockBox.getDepth();
+
+				unsigned int subresource = D3D11CalcSubresource(mSubresourceIndex, mLockBox.front, mParentTexture->getNumMipmaps()+1);
+				mDevice.getImmediateContext()->CopySubresourceRegion(mParentTexture->getTextureResource(), subresource, mLockBox.left, mLockBox.top, mSubresourceIndex, mStagingBuffer, subresource, &dstBoxDx11);
+			}
+		}
+	}
+ 
+	void D3D11HardwarePixelBuffer::unlockImpl(void)
+	{
+		if(mUsage == HBU_STATIC)
+			_unmapstagingbuffer();
+		else if(mUsage & HBU_DYNAMIC)
+ 		{
+			if(mCurrentLockOptions == HBL_READ_ONLY || mCurrentLockOptions == HBL_READ_WRITE || mCurrentLockOptions == HBL_WRITE_ONLY)
+			{
+				size_t sizeinbytes = D3D11Mappings::_getSizeInBytes(mParentTexture->getFormat(), mParentTexture->getWidth(), mParentTexture->getHeight());
+
+				void *data = _map(mParentTexture->getTextureResource(), D3D11_MAP_WRITE_DISCARD);
+
+				memcpy(data, mCurrentLock.data, sizeinbytes);
+
+				// unmap the texture and the staging buffer
+				_unmap(mParentTexture->getTextureResource());
+
+				_unmapstagingbuffer(false);
+ 			}
+			else
+				_unmap(mParentTexture->getTextureResource());
+ 		}
+ 		else
+			_unmapstaticbuffer();
+	}
+
+	D3D11_BOX D3D11HardwarePixelBuffer::convertBoxToDx11Box(const Box &inBox) const
+	{
+		D3D11_BOX res;
+		res.left	= static_cast<UINT>(inBox.left);
+		res.top		= static_cast<UINT>(inBox.top);
+		res.front	= static_cast<UINT>(inBox.front);
+		res.right	= static_cast<UINT>(inBox.right);
+		res.bottom	= static_cast<UINT>(inBox.bottom);
+		res.back	= static_cast<UINT>(inBox.back);
+
+		return res;
+	}
+
+	void D3D11HardwarePixelBuffer::blit(const HardwarePixelBufferPtr &rsrc, const Box &srcBox, const Box &dstBox)
+	{
+		if (
+			(srcBox.getWidth() != dstBox.getWidth())
+			|| (srcBox.getHeight() != dstBox.getHeight())
+			|| (srcBox.getDepth() != dstBox.getDepth())
+			)
+		{
+			CM_EXCEPT(RenderingAPIException, 
+				"D3D11 device cannot copy a subresource - source and dest size are not the same and they have to be the same in DX11.");
+		}
+
+		D3D11_BOX srcBoxDx11 = convertBoxToDx11Box(srcBox);
+		D3D11HardwarePixelBuffer* rsrcDx11 = static_cast<D3D11HardwarePixelBuffer*>(rsrc.get());
+
+		switch(mParentTexture->getTextureType()) {
+		case TEX_TYPE_1D:
+			{
+
+				mDevice.getImmediateContext()->CopySubresourceRegion(
+					mParentTexture->GetTex1D(), 
+					static_cast<UINT>(mSubresourceIndex),
+					static_cast<UINT>(dstBox.left),
+					0,
+					0,
+					rsrcDx11->mParentTexture->GetTex1D(),
+					static_cast<UINT>(rsrcDx11->mSubresourceIndex),
+					&srcBoxDx11);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot copy 1d subresource Region\nError Description:" + errorDescription);
+				}			
+			}
+			break;
+		case TEX_TYPE_CUBE_MAP:
+		case TEX_TYPE_2D:
+			{
+				mDevice.getImmediateContext()->CopySubresourceRegion(
+					mParentTexture->GetTex2D(), 
+					D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mFace, mParentTexture->getNumMipmaps()+1),
+					static_cast<UINT>(dstBox.left),
+					static_cast<UINT>(dstBox.top),
+					mFace,
+					rsrcDx11->mParentTexture->GetTex2D(),
+					static_cast<UINT>(rsrcDx11->mSubresourceIndex),
+					&srcBoxDx11);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot copy 2d subresource Region\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_2D_ARRAY:
+			{
+				mDevice.getImmediateContext()->CopySubresourceRegion(
+					mParentTexture->GetTex2D(), 
+					D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), srcBox.front, mParentTexture->getNumMipmaps()+1),
+					static_cast<UINT>(dstBox.left),
+					static_cast<UINT>(dstBox.top),
+					srcBox.front,
+					rsrcDx11->mParentTexture->GetTex2D(),
+					static_cast<UINT>(rsrcDx11->mSubresourceIndex),
+					&srcBoxDx11);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot copy 2d subresource Region\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		case TEX_TYPE_3D:
+			{
+				mDevice.getImmediateContext()->CopySubresourceRegion(
+					mParentTexture->GetTex3D(), 
+					static_cast<UINT>(mSubresourceIndex),
+					static_cast<UINT>(dstBox.left),
+					static_cast<UINT>(dstBox.top),
+					static_cast<UINT>(dstBox.front),
+					rsrcDx11->mParentTexture->GetTex3D(),
+					static_cast<UINT>(rsrcDx11->mSubresourceIndex),
+					&srcBoxDx11);
+				if (mDevice.hasError())
+				{
+					String errorDescription = mDevice.getErrorDescription();
+					CM_EXCEPT(RenderingAPIException, "D3D11 device cannot copy 3d subresource Region\nError Description:" + errorDescription);
+				}
+			}
+			break;
+		}
+
+		_genMipmaps();
+	}
+ 
+	void D3D11HardwarePixelBuffer::blitFromMemory(const PixelData& src, const Box& dstBox)
+	{
+		bool isCompressed = false;
+		switch(mFormat)
+		{
+		case PF_DXT1:
+		case PF_DXT2:
+		case PF_DXT3:
+		case PF_DXT4:
+		case PF_DXT5:
+			isCompressed = true;
+			break;
+		default:
+
+			break;
+		}
+
+		if (isCompressed && (dstBox.getWidth() % 4 != 0 || dstBox.getHeight() % 4 != 0 ))
+		{
+			return;
+		}
+
+
+		// for scoped deletion of conversion buffer
+		PixelData converted = src;
+
+		D3D11_BOX dstBoxDx11 = convertBoxToDx11Box(dstBox);
+		dstBoxDx11.front = 0;
+		dstBoxDx11.back = converted.getDepth();
+
+		// convert to pixelbuffer's native format if necessary
+		if (src.format != mFormat)
+		{
+			MemoryDataStreamPtr buf(new MemoryDataStream(PixelUtil::getMemorySize(src.getWidth(), src.getHeight(), src.getDepth(), mFormat)));
+			converted = PixelData(src.getWidth(), src.getHeight(), src.getDepth(), mFormat, buf->getPtr());
+			PixelUtil::bulkPixelConversion(src, converted);
+		}
+
+		if (mUsage & HBU_DYNAMIC)
+		{
+			size_t sizeinbytes;
+			if (PixelUtil::isCompressed(converted.format))
+ 			{
+				// D3D wants the width of one row of cells in bytes
+				if (converted.format == PF_DXT1)
+				{
+					// 64 bits (8 bytes) per 4x4 block
+					sizeinbytes = std::max<size_t>(1, converted.getWidth() / 4) * std::max<size_t>(1, converted.getHeight() / 4) * 8;
+				}
+				else
+				{
+					// 128 bits (16 bytes) per 4x4 block
+					sizeinbytes = std::max<size_t>(1, converted.getWidth() / 4) * std::max<size_t>(1, converted.getHeight() / 4) * 16;
+				}
+ 			}
+ 			else
+ 			{
+				sizeinbytes = converted.getHeight() * converted.getWidth() * PixelUtil::getNumElemBytes(converted.format);
+ 			}
+ 
+			const PixelData& locked = lock(dstBox, HBL_WRITE_ONLY_DISCARD);
+
+			memcpy(locked.data, converted.data, sizeinbytes);
+
+			unlock();
+ 		}
+ 		else
+		{
+			size_t rowWidth;
+			if (PixelUtil::isCompressed(converted.format))
+ 			{
+				// D3D wants the width of one row of cells in bytes
+				if (converted.format == PF_DXT1)
+ 				{
+					// 64 bits (8 bytes) per 4x4 block
+					rowWidth = (converted.rowPitch / 4) * 8;
+				}
+				else
+				{
+					// 128 bits (16 bytes) per 4x4 block
+					rowWidth = (converted.rowPitch / 4) * 16;
+ 				}
+ 			}
+			else
+ 			{
+				rowWidth = converted.rowPitch * PixelUtil::getNumElemBytes(converted.format);
+			}
+
+			switch(mParentTexture->getTextureType()) {
+			case TEX_TYPE_1D:
+ 				{
+
+					mDevice.getImmediateContext()->UpdateSubresource( 
+						mParentTexture->GetTex1D(), 
+						0,
+						&dstBoxDx11,
+						converted.data,
+						rowWidth,
+						0 );
+					if (mDevice.hasError())
+					{
+						String errorDescription = mDevice.getErrorDescription();
+						CM_EXCEPT(RenderingAPIException, "D3D11 device cannot update 1d subresource\nError Description:" + errorDescription);
+					}
+ 				}
+				break;
+			case TEX_TYPE_CUBE_MAP:
+			case TEX_TYPE_2D:
+ 				{
+					mDevice.getImmediateContext()->UpdateSubresource( 
+						mParentTexture->GetTex2D(), 
+						D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), mFace, mParentTexture->getNumMipmaps()+1),
+						&dstBoxDx11,
+						converted.data,
+						rowWidth,
+						0 );
+					if (mDevice.hasError())
+					{
+						String errorDescription = mDevice.getErrorDescription();
+						CM_EXCEPT(RenderingAPIException, "D3D11 device cannot update 2d subresource\nError Description:" + errorDescription);
+					}
+ 				}
+				break;
+			case TEX_TYPE_2D_ARRAY:
+ 				{
+					mDevice.getImmediateContext()->UpdateSubresource( 
+						mParentTexture->GetTex2D(), 
+						D3D11CalcSubresource(static_cast<UINT>(mSubresourceIndex), src.front, mParentTexture->getNumMipmaps()+1),
+						&dstBoxDx11,
+						converted.data,
+						rowWidth,
+						0 );
+					if (mDevice.hasError())
+ 					{
+						String errorDescription = mDevice.getErrorDescription();
+						CM_EXCEPT(RenderingAPIException, "D3D11 device cannot update 2d array subresource\nError Description:" + errorDescription);
+				}
+				}
+				break;
+			case TEX_TYPE_3D:
+				{
+					// copied from dx9
+					size_t sliceWidth;
+					if (PixelUtil::isCompressed(converted.format))
+					{
+						// D3D wants the width of one slice of cells in bytes
+						if (converted.format == PF_DXT1)
+						{
+							// 64 bits (8 bytes) per 4x4 block
+							sliceWidth = (converted.slicePitch / 16) * 8;
+						}
+						else
+						{
+							// 128 bits (16 bytes) per 4x4 block
+							sliceWidth = (converted.slicePitch / 16) * 16;
+						}
+
+ 					}
+ 					else
+ 					{
+						sliceWidth = converted.slicePitch * PixelUtil::getNumElemBytes(converted.format);
+ 					}
+ 
+					mDevice.getImmediateContext()->UpdateSubresource( 
+						mParentTexture->GetTex3D(), 
+						static_cast<UINT>(mSubresourceIndex),
+						&dstBoxDx11,
+						converted.data,
+						rowWidth,
+						sliceWidth
+						);
+					if (mDevice.hasError())
+					{
+						String errorDescription = mDevice.getErrorDescription();
+						CM_EXCEPT(RenderingAPIException, "D3D11 device cannot update 3d subresource\nError Description:" + errorDescription);
+					}
+ 				}
+				break;
+			}
+ 
+			if (!isCompressed)
+			{
+				_genMipmaps();
+ 			}
+		}	
+ 	}
+
+	void D3D11HardwarePixelBuffer::blitToMemory(const Box &srcBox, const PixelData &dst)
+	{
+		if(mParentTexture->getTextureType() != TEX_TYPE_2D)
+		{
+			CM_EXCEPT(NotImplementedException, "Only implemeted for 2D buffers.");
+		}
+
+		PixelData lockedData = lock(srcBox, HardwareBuffer::HBL_READ_ONLY);
+
+		if(dst.getConsecutiveSize() != lockedData.getConsecutiveSize())
+		{
+			unlock();
+
+			CM_EXCEPT(RenderingAPIException, "Size of the provided buffer (" + toString(dst.getConsecutiveSize()) + "), doesn't "
+				+ "match the size of the texture buffer (" + toString(lockedData.getConsecutiveSize()) + ").");
+		}
+
+		memcpy(dst.data, lockedData.data, lockedData.getConsecutiveSize());
+
+		unlock();
+	}
+  
+	void D3D11HardwarePixelBuffer::_genMipmaps()
+	{
+        if(mParentTexture->HasAutoMipMapGenerationEnabled())
+ 		{
+            ID3D11ShaderResourceView *pShaderResourceView = mParentTexture->getTexture();
+			mDevice.getImmediateContext()->GenerateMips(pShaderResourceView);
+			if (mDevice.hasError())
+			{
+				String errorDescription = mDevice.getErrorDescription();
+				CM_EXCEPT(RenderingAPIException, "D3D11 device cannot generate mips\nError Description:" + errorDescription);
+			}	
+		}
+	}
+    
+	RenderTexture *D3D11HardwarePixelBuffer::getRenderTarget(UINT32 zoffset)
+	{
+		assert(mUsage & TU_RENDERTARGET);
+		assert(zoffset < mDepth);
+		return mSliceTRT[zoffset];
+	}
+
+	D3D11Texture * D3D11HardwarePixelBuffer::getParentTexture() const
+	{
+		return mParentTexture;
+	}
+    
+	UINT32 D3D11HardwarePixelBuffer::getSubresourceIndex() const
+	{
+		return mSubresourceIndex;
+	}
+   
+	UINT32 D3D11HardwarePixelBuffer::getFace() const
+	{
+		return mFace;
+	}
+   
+	void D3D11HardwarePixelBuffer::createStagingBuffer()
+	{
+		switch (mParentTexture->getTextureType())
+		{
+		case TEX_TYPE_1D:
+			{
+				D3D11_TEXTURE1D_DESC desc;
+				mParentTexture->GetTex1D()->GetDesc(&desc);
+
+				desc.BindFlags = 0;
+				desc.MiscFlags = 0;
+				desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE | D3D11_CPU_ACCESS_READ;
+				desc.Usage = D3D11_USAGE_STAGING;
+
+				mDevice.getD3D11Device()->CreateTexture1D(&desc, NULL, (ID3D11Texture1D**)(&mStagingBuffer));
+			} 					
+			break;
+		case TEX_TYPE_2D:
+		case TEX_TYPE_CUBE_MAP:
+		case TEX_TYPE_2D_ARRAY:
+			{
+				D3D11_TEXTURE2D_DESC desc;
+				mParentTexture->GetTex2D()->GetDesc(&desc);
+
+				desc.BindFlags = 0;
+				desc.MiscFlags = 0;
+				desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE | D3D11_CPU_ACCESS_READ;
+				desc.Usage = D3D11_USAGE_STAGING;
+
+				mDevice.getD3D11Device()->CreateTexture2D(&desc, NULL, (ID3D11Texture2D**)(&mStagingBuffer));
+			}
+			break;
+		case TEX_TYPE_3D:
+			{
+				D3D11_TEXTURE3D_DESC desc;
+				mParentTexture->GetTex3D()->GetDesc(&desc);
+
+				desc.BindFlags = 0;
+				desc.MiscFlags = 0;
+				desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE | D3D11_CPU_ACCESS_READ;
+				desc.Usage = D3D11_USAGE_STAGING;
+
+				mDevice.getD3D11Device()->CreateTexture3D(&desc, NULL, (ID3D11Texture3D**)(&mStagingBuffer));
+			}
+			break;
+		}
+	}
+}

+ 42 - 3
CamelotD3D11RenderSystem/Source/CmD3D11Mappings.cpp

@@ -431,6 +431,19 @@ namespace CamelotEngine
 		outColour[3] = inColour.a;	
 	}
 
+	D3D11_BOX D3D11Mappings::toDx11Box(const Box &inBox)
+	{
+		D3D11_BOX res;
+		res.left	= static_cast<UINT>(inBox.left);
+		res.top		= static_cast<UINT>(inBox.top);
+		res.front	= static_cast<UINT>(inBox.front);
+		res.right	= static_cast<UINT>(inBox.right);
+		res.bottom	= static_cast<UINT>(inBox.bottom);
+		res.back	= static_cast<UINT>(inBox.back);
+
+		return res;
+	}
+
 	PixelFormat D3D11Mappings::_getPF(DXGI_FORMAT d3dPF)
 	{
 		switch(d3dPF)
@@ -786,7 +799,7 @@ namespace CamelotEngine
 		}
 	}
 	//---------------------------------------------------------------------
-	size_t D3D11Mappings::_getSizeInBytes(PixelFormat pf, size_t xcount, size_t ycount)
+	UINT32 D3D11Mappings::_getSizeInBytes(PixelFormat pf, UINT32 xcount, UINT32 ycount)
 	{
 		if(xcount == 0 || ycount == 0)
 			return 0;
@@ -797,12 +810,12 @@ namespace CamelotEngine
 			if (pf == PF_DXT1)
 			{
 				// 64 bits (8 bytes) per 4x4 block
-				return std::max<size_t>(1, xcount / 4) * std::max<size_t>(1, ycount / 4) * 8;
+				return std::max<UINT32>(1, xcount / 4) * std::max<UINT32>(1, ycount / 4) * 8;
 			}
 			else
 			{
 				// 128 bits (16 bytes) per 4x4 block
-				return std::max<size_t>(1, xcount / 4) * std::max<size_t>(1, ycount / 4) * 16;
+				return std::max<UINT32>(1, xcount / 4) * std::max<UINT32>(1, ycount / 4) * 16;
 			}
 		}
 		else
@@ -890,4 +903,30 @@ namespace CamelotEngine
 
 		return flags;
 	}
+
+	D3D11_MAP D3D11Mappings::_getLockOptions(LockOptions lockOptions)
+	{
+		switch(lockOptions)
+		{
+		case HBL_WRITE_ONLY_NO_OVERWRITE:
+			return D3D11_MAP_WRITE_NO_OVERWRITE;
+			break;
+		case HBL_READ_WRITE:
+			return D3D11_MAP_READ_WRITE;
+			break;
+		case HBL_WRITE_ONLY_DISCARD:
+			return D3D11_MAP_WRITE_DISCARD;
+			break;
+		case HBL_READ_ONLY:
+			return D3D11_MAP_READ;
+			break;
+		case HBL_WRITE_ONLY:
+			return D3D11_MAP_WRITE;
+			break;
+		default: 
+			break;
+		};
+
+		CM_EXCEPT(RenderingAPIException, "Invalid lock option. No DX11 equivalent of: " + toString(lockOptions));
+	}
 }

+ 6 - 0
CamelotD3D11RenderSystem/Source/CmD3D11RenderTexture.cpp

@@ -0,0 +1,6 @@
+#include "CmD3D11RenderTexture.h"
+
+namespace CamelotEngine
+{
+
+}

+ 732 - 732
CamelotD3D11RenderSystem/Source/CmD3D11RenderWindow.cpp

@@ -8,771 +8,771 @@
 
 namespace CamelotEngine
 {
-	D3D11RenderWindow::D3D11RenderWindow(D3D11Device& device, IDXGIFactory* DXGIFactory)
-		: RenderWindow()
-		, mDevice(device)
-		, mDXGIFactory(DXGIFactory)
-		, mIsExternal(false)
-		, mSizing(false)
-		, mClosed(false)
-		, mHidden(false)
-		, mSwitchingFullscreen(false)
-		, mDisplayFrequency(0)
-		, mRenderTargetView(nullptr)
-		, mDepthStencilView(nullptr)
-		, mBackBuffer(nullptr)
-		, mSwapChain(nullptr)
-		, mHWnd(0)
-	{
-		ZeroMemory(&mSwapChainDesc, sizeof(DXGI_SWAP_CHAIN_DESC));
-	}
-
-	D3D11RenderWindow::~D3D11RenderWindow()
-	{
-		destroy();
+	D3D11RenderWindow::D3D11RenderWindow(D3D11Device& device, IDXGIFactory* DXGIFactory)
+		: RenderWindow()
+		, mDevice(device)
+		, mDXGIFactory(DXGIFactory)
+		, mIsExternal(false)
+		, mSizing(false)
+		, mClosed(false)
+		, mHidden(false)
+		, mSwitchingFullscreen(false)
+		, mDisplayFrequency(0)
+		, mRenderTargetView(nullptr)
+		, mDepthStencilView(nullptr)
+		, mBackBuffer(nullptr)
+		, mSwapChain(nullptr)
+		, mHWnd(0)
+	{
+		ZeroMemory(&mSwapChainDesc, sizeof(DXGI_SWAP_CHAIN_DESC));
 	}
 
-	void D3D11RenderWindow::initialize(const String& name, unsigned int width, unsigned int height,
-		bool fullScreen, const NameValuePairList *miscParams)
-	{
-		mFSAAType.Count = 1;
-		mFSAAType.Quality = 0;
-		mFSAA = 0;
-		mFSAAHint = "";
-		mVSync = false;
-		mVSyncInterval = 1;
-		HWND parentHWnd = 0;
-		HWND externalHandle = 0;
-		String title = name;
-		int left = -1; // Defaults to screen center
-		int top = -1; // Defaults to screen center
-		String border = "";
-		bool outerSize = false;
-		bool enableDoubleClick = false;
-
-		unsigned int colourDepth = 32;
-		bool depthBuffer = true;
-
-		if(miscParams)
-		{
-			// Get variable-length params
-			NameValuePairList::const_iterator opt;
-			// vsync	[parseBool]
-			opt = miscParams->find("vsync");
-			if(opt != miscParams->end())
-				mVSync = parseBool(opt->second);
-			// vsyncInterval	[parseUnsignedInt]
-			opt = miscParams->find("vsyncInterval");
-			if(opt != miscParams->end())
-				mVSyncInterval = parseUnsignedInt(opt->second);
-			// hidden	[parseBool]
-			opt = miscParams->find("hidden");
-			if(opt != miscParams->end())
-				mHidden = parseBool(opt->second);
-			// displayFrequency
-			opt = miscParams->find("displayFrequency");
-			if(opt != miscParams->end())
-				mDisplayFrequency = parseUnsignedInt(opt->second);
-			// colourDepth
-			opt = miscParams->find("colourDepth");
-			if(opt != miscParams->end())
-				colourDepth = parseUnsignedInt(opt->second);
-			// depthBuffer [parseBool]
-			opt = miscParams->find("depthBuffer");
-			if(opt != miscParams->end())
-				depthBuffer = parseBool(opt->second);
-			// FSAA type
-			opt = miscParams->find("FSAA");
-			if(opt != miscParams->end())
-				mFSAA = parseUnsignedInt(opt->second);
-			// FSAA quality
-			opt = miscParams->find("FSAAHint");
-			if(opt != miscParams->end())
-				mFSAAHint = opt->second;
-			// sRGB?
-			opt = miscParams->find("gamma");
-			if(opt != miscParams->end())
-				mHwGamma = parseBool(opt->second);
-			// left (x)
-			opt = miscParams->find("left");
-			if(opt != miscParams->end())
-				left = parseInt(opt->second);
-			// top (y)
-			opt = miscParams->find("top");
-			if(opt != miscParams->end())
-				top = parseInt(opt->second);
-			// Window title
-			opt = miscParams->find("title");
-			if(opt != miscParams->end())
-				title = opt->second;
-			// parentWindowHandle		-> parentHWnd
-			opt = miscParams->find("parentWindowHandle");
-			if(opt != miscParams->end())
-				parentHWnd = (HWND)parseUnsignedInt(opt->second);
-			// externalWindowHandle		-> externalHandle
-			opt = miscParams->find("externalWindowHandle");
-			if(opt != miscParams->end())
-				externalHandle = (HWND)parseUnsignedInt(opt->second);
-			// window border style
-			opt = miscParams->find("border");
-			if(opt != miscParams->end())
-				border = opt->second;
-			// set outer dimensions?
-			opt = miscParams->find("outerDimensions");
-			if(opt != miscParams->end())
-				outerSize = parseBool(opt->second);
-			// enable double click messages
-			opt = miscParams->find("enableDoubleClick");
-			if(opt != miscParams->end())
-				enableDoubleClick = parseBool(opt->second);
-		}
-
-		mName = name;
-		mIsFullScreen = fullScreen;
-		mColourDepth = colourDepth;
-		mWidth = mHeight = mLeft = mTop = 0;
-
-		mActive = true;
-		mClosed = false;
-
-		// Destroy current window if any
-		if(mHWnd)
-			destroy();
-
-		if (!externalHandle)
-		{
-			DWORD dwStyle = (mHidden ? 0 : WS_VISIBLE) | WS_CLIPCHILDREN;
-			RECT rc;
-
-			mWidth = width;
-			mHeight = height;
-			mTop = top;
-			mLeft = left;
-
-			if (!fullScreen)
-			{
-				if (parentHWnd)
-				{
-					dwStyle |= WS_CHILD;
-				}
-				else
-				{
-					if (border == "none")
-						dwStyle |= WS_POPUP;
-					else if (border == "fixed")
-						dwStyle |= WS_OVERLAPPED | WS_BORDER | WS_CAPTION |
-						WS_SYSMENU | WS_MINIMIZEBOX;
-					else
-						dwStyle |= WS_OVERLAPPEDWINDOW;
-				}
-
-				if (!outerSize)
-				{
-					// Calculate window dimensions required
-					// to get the requested client area
-					SetRect(&rc, 0, 0, mWidth, mHeight);
-					AdjustWindowRect(&rc, dwStyle, false);
-					mWidth = rc.right - rc.left;
-					mHeight = rc.bottom - rc.top;
-
-					// Clamp width and height to the desktop dimensions
-					int screenw = GetSystemMetrics(SM_CXSCREEN);
-					int screenh = GetSystemMetrics(SM_CYSCREEN);
-					if ((int)mWidth > screenw)
-						mWidth = screenw;
-					if ((int)mHeight > screenh)
-						mHeight = screenh;
-					if (mLeft < 0)
-						mLeft = (screenw - mWidth) / 2;
-					if (mTop < 0)
-						mTop = (screenh - mHeight) / 2;
-				}
-			}
-			else
-			{
-				dwStyle |= WS_POPUP;
-				mTop = mLeft = 0;
-			}
-
-			UINT classStyle = 0;
-			if (enableDoubleClick)
-				classStyle |= CS_DBLCLKS;
-
-			HINSTANCE hInst = NULL;
-
-			// Register the window class
-			// Allow 4 bytes of window data for D3D11RenderWindow pointer
-			WNDCLASS wc = { classStyle, WindowEventUtilities::_WndProc, 0, 0, hInst,
-				LoadIcon(0, IDI_APPLICATION), LoadCursor(NULL, IDC_ARROW),
-				(HBRUSH)GetStockObject(BLACK_BRUSH), 0, "D3D11Wnd" };	
-
-
-			RegisterClass(&wc);
-
-			// Create our main window
-			// Pass pointer to self
-			mIsExternal = false;
-			mHWnd = CreateWindow("D3D11Wnd", title.c_str(), dwStyle,
-				mLeft, mTop, mWidth, mHeight, parentHWnd, 0, hInst, this);
-
-			WindowEventUtilities::_addRenderWindow(this);
-		}
-		else
-		{
-			mHWnd = externalHandle;
-			mIsExternal = true;
-		}
-
-		RECT rc;
-		// top and left represent outer window coordinates
-		GetWindowRect(mHWnd, &rc);
-		mTop = rc.top;
-		mLeft = rc.left;
-		// width and height represent interior drawable area
-		GetClientRect(mHWnd, &rc);
-		mWidth = rc.right;
-		mHeight = rc.bottom;
-
-		_createSwapChain();
-		_createSizeDependedD3DResources();
-		mDXGIFactory->MakeWindowAssociation(mHWnd, NULL);
-		setHidden(mHidden);
+	D3D11RenderWindow::~D3D11RenderWindow()
+	{
+		destroy();
+	}
+
+	void D3D11RenderWindow::initialize(const String& name, unsigned int width, unsigned int height,
+		bool fullScreen, const NameValuePairList *miscParams)
+	{
+		mFSAAType.Count = 1;
+		mFSAAType.Quality = 0;
+		mFSAA = 0;
+		mFSAAHint = "";
+		mVSync = false;
+		mVSyncInterval = 1;
+		HWND parentHWnd = 0;
+		HWND externalHandle = 0;
+		String title = name;
+		int left = -1; // Defaults to screen center
+		int top = -1; // Defaults to screen center
+		String border = "";
+		bool outerSize = false;
+		bool enableDoubleClick = false;
+
+		unsigned int colourDepth = 32;
+		bool depthBuffer = true;
+
+		if(miscParams)
+		{
+			// Get variable-length params
+			NameValuePairList::const_iterator opt;
+			// vsync	[parseBool]
+			opt = miscParams->find("vsync");
+			if(opt != miscParams->end())
+				mVSync = parseBool(opt->second);
+			// vsyncInterval	[parseUnsignedInt]
+			opt = miscParams->find("vsyncInterval");
+			if(opt != miscParams->end())
+				mVSyncInterval = parseUnsignedInt(opt->second);
+			// hidden	[parseBool]
+			opt = miscParams->find("hidden");
+			if(opt != miscParams->end())
+				mHidden = parseBool(opt->second);
+			// displayFrequency
+			opt = miscParams->find("displayFrequency");
+			if(opt != miscParams->end())
+				mDisplayFrequency = parseUnsignedInt(opt->second);
+			// colourDepth
+			opt = miscParams->find("colourDepth");
+			if(opt != miscParams->end())
+				colourDepth = parseUnsignedInt(opt->second);
+			// depthBuffer [parseBool]
+			opt = miscParams->find("depthBuffer");
+			if(opt != miscParams->end())
+				depthBuffer = parseBool(opt->second);
+			// FSAA type
+			opt = miscParams->find("FSAA");
+			if(opt != miscParams->end())
+				mFSAA = parseUnsignedInt(opt->second);
+			// FSAA quality
+			opt = miscParams->find("FSAAHint");
+			if(opt != miscParams->end())
+				mFSAAHint = opt->second;
+			// sRGB?
+			opt = miscParams->find("gamma");
+			if(opt != miscParams->end())
+				mHwGamma = parseBool(opt->second);
+			// left (x)
+			opt = miscParams->find("left");
+			if(opt != miscParams->end())
+				left = parseInt(opt->second);
+			// top (y)
+			opt = miscParams->find("top");
+			if(opt != miscParams->end())
+				top = parseInt(opt->second);
+			// Window title
+			opt = miscParams->find("title");
+			if(opt != miscParams->end())
+				title = opt->second;
+			// parentWindowHandle		-> parentHWnd
+			opt = miscParams->find("parentWindowHandle");
+			if(opt != miscParams->end())
+				parentHWnd = (HWND)parseUnsignedInt(opt->second);
+			// externalWindowHandle		-> externalHandle
+			opt = miscParams->find("externalWindowHandle");
+			if(opt != miscParams->end())
+				externalHandle = (HWND)parseUnsignedInt(opt->second);
+			// window border style
+			opt = miscParams->find("border");
+			if(opt != miscParams->end())
+				border = opt->second;
+			// set outer dimensions?
+			opt = miscParams->find("outerDimensions");
+			if(opt != miscParams->end())
+				outerSize = parseBool(opt->second);
+			// enable double click messages
+			opt = miscParams->find("enableDoubleClick");
+			if(opt != miscParams->end())
+				enableDoubleClick = parseBool(opt->second);
+		}
+
+		mName = name;
+		mIsFullScreen = fullScreen;
+		mColourDepth = colourDepth;
+		mWidth = mHeight = mLeft = mTop = 0;
+
+		mActive = true;
+		mClosed = false;
+
+		// Destroy current window if any
+		if(mHWnd)
+			destroy();
+
+		if (!externalHandle)
+		{
+			DWORD dwStyle = (mHidden ? 0 : WS_VISIBLE) | WS_CLIPCHILDREN;
+			RECT rc;
+
+			mWidth = width;
+			mHeight = height;
+			mTop = top;
+			mLeft = left;
+
+			if (!fullScreen)
+			{
+				if (parentHWnd)
+				{
+					dwStyle |= WS_CHILD;
+				}
+				else
+				{
+					if (border == "none")
+						dwStyle |= WS_POPUP;
+					else if (border == "fixed")
+						dwStyle |= WS_OVERLAPPED | WS_BORDER | WS_CAPTION |
+						WS_SYSMENU | WS_MINIMIZEBOX;
+					else
+						dwStyle |= WS_OVERLAPPEDWINDOW;
+				}
+
+				if (!outerSize)
+				{
+					// Calculate window dimensions required
+					// to get the requested client area
+					SetRect(&rc, 0, 0, mWidth, mHeight);
+					AdjustWindowRect(&rc, dwStyle, false);
+					mWidth = rc.right - rc.left;
+					mHeight = rc.bottom - rc.top;
+
+					// Clamp width and height to the desktop dimensions
+					int screenw = GetSystemMetrics(SM_CXSCREEN);
+					int screenh = GetSystemMetrics(SM_CYSCREEN);
+					if ((int)mWidth > screenw)
+						mWidth = screenw;
+					if ((int)mHeight > screenh)
+						mHeight = screenh;
+					if (mLeft < 0)
+						mLeft = (screenw - mWidth) / 2;
+					if (mTop < 0)
+						mTop = (screenh - mHeight) / 2;
+				}
+			}
+			else
+			{
+				dwStyle |= WS_POPUP;
+				mTop = mLeft = 0;
+			}
+
+			UINT classStyle = 0;
+			if (enableDoubleClick)
+				classStyle |= CS_DBLCLKS;
+
+			HINSTANCE hInst = NULL;
+
+			// Register the window class
+			// Allow 4 bytes of window data for D3D11RenderWindow pointer
+			WNDCLASS wc = { classStyle, WindowEventUtilities::_WndProc, 0, 0, hInst,
+				LoadIcon(0, IDI_APPLICATION), LoadCursor(NULL, IDC_ARROW),
+				(HBRUSH)GetStockObject(BLACK_BRUSH), 0, "D3D11Wnd" };	
+
+
+			RegisterClass(&wc);
+
+			// Create our main window
+			// Pass pointer to self
+			mIsExternal = false;
+			mHWnd = CreateWindow("D3D11Wnd", title.c_str(), dwStyle,
+				mLeft, mTop, mWidth, mHeight, parentHWnd, 0, hInst, this);
+
+			WindowEventUtilities::_addRenderWindow(this);
+		}
+		else
+		{
+			mHWnd = externalHandle;
+			mIsExternal = true;
+		}
+
+		RECT rc;
+		// top and left represent outer window coordinates
+		GetWindowRect(mHWnd, &rc);
+		mTop = rc.top;
+		mLeft = rc.left;
+		// width and height represent interior drawable area
+		GetClientRect(mHWnd, &rc);
+		mWidth = rc.right;
+		mHeight = rc.bottom;
+
+		_createSwapChain();
+		_createSizeDependedD3DResources();
+		mDXGIFactory->MakeWindowAssociation(mHWnd, NULL);
+		setHidden(mHidden);
 	}
 
 	void D3D11RenderWindow::destroy()
 	{
-		_destroySizeDependedD3DResources();
-
-		mActive = false;
+		_destroySizeDependedD3DResources();
+
+		mActive = false;
 		mClosed = true;
 
-		SAFE_RELEASE(mSwapChain);
-
-		if (mHWnd && !mIsExternal)
-		{
-			WindowEventUtilities::_removeRenderWindow(this);
-			DestroyWindow(mHWnd);
-		}
-
+		SAFE_RELEASE(mSwapChain);
+
+		if (mHWnd && !mIsExternal)
+		{
+			WindowEventUtilities::_removeRenderWindow(this);
+			DestroyWindow(mHWnd);
+		}
+
 		mHWnd = nullptr;
 	}
 
-	void D3D11RenderWindow::swapBuffers(bool waitForVSync)
-	{
-		if(mDevice.getD3D11Device() != nullptr)
-		{
-			HRESULT hr = mSwapChain->Present(waitForVSync ? mVSyncInterval : 0, 0);
-
-			if( FAILED(hr) )
-				CM_EXCEPT(RenderingAPIException, "Error Presenting surfaces");
-		}
+	void D3D11RenderWindow::swapBuffers(bool waitForVSync)
+	{
+		if(mDevice.getD3D11Device() != nullptr)
+		{
+			HRESULT hr = mSwapChain->Present(waitForVSync ? mVSyncInterval : 0, 0);
+
+			if( FAILED(hr) )
+				CM_EXCEPT(RenderingAPIException, "Error Presenting surfaces");
+		}
 	}
 
-	void D3D11RenderWindow::reposition(int top, int left)
-	{
-		if (mHWnd && !mIsFullScreen)
-		{
-			SetWindowPos(mHWnd, 0, top, left, 0, 0,
-				SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE);
-		}
-	}
-
-	void D3D11RenderWindow::resize(unsigned int width, unsigned int height)
-	{
-		if (mHWnd && !mIsFullScreen)
-		{
-			RECT rc = { 0, 0, width, height };
-			AdjustWindowRect(&rc, GetWindowLong(mHWnd, GWL_STYLE), false);
-			width = rc.right - rc.left;
-			height = rc.bottom - rc.top;
-			SetWindowPos(mHWnd, 0, 0, 0, width, height,
-				SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE);
-		}
-	}
-
-	void D3D11RenderWindow::windowMovedOrResized()
-	{
-		if (!mHWnd || IsIconic(mHWnd))
-			return;
-
-		RECT rc;
-		// top and left represent outer window position
-		GetWindowRect(mHWnd, &rc);
-		mTop = rc.top;
-		mLeft = rc.left;
-		// width and height represent drawable area only
-		GetClientRect(mHWnd, &rc);
-		unsigned int width = rc.right - rc.left;
-		unsigned int height = rc.bottom - rc.top;
-
-		if (width == 0) 
-			width = 1;
-		if (height == 0)
-			height = 1;
-
-		if (mWidth == width && mHeight == height)
-			return;
-
-		_resizeSwapChainBuffers(width, height);
+	void D3D11RenderWindow::reposition(int top, int left)
+	{
+		if (mHWnd && !mIsFullScreen)
+		{
+			SetWindowPos(mHWnd, 0, top, left, 0, 0,
+				SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE);
+		}
 	}
 
-	void D3D11RenderWindow::setActive(bool state)
-	{
-		if (mHWnd && mSwapChain)
-		{
-			if (state)
-			{
-				ShowWindow(mHWnd, SW_RESTORE);
-				mSwapChain->SetFullscreenState(mIsFullScreen, nullptr);
-			}
-			else
-			{
-				ShowWindow(mHWnd, SW_SHOWMINIMIZED);
-				mSwapChain->SetFullscreenState(FALSE, nullptr);
-			}
-		}
-
-		RenderWindow::setActive(state);
+	void D3D11RenderWindow::resize(unsigned int width, unsigned int height)
+	{
+		if (mHWnd && !mIsFullScreen)
+		{
+			RECT rc = { 0, 0, width, height };
+			AdjustWindowRect(&rc, GetWindowLong(mHWnd, GWL_STYLE), false);
+			width = rc.right - rc.left;
+			height = rc.bottom - rc.top;
+			SetWindowPos(mHWnd, 0, 0, 0, width, height,
+				SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE);
+		}
 	}
 
-	void D3D11RenderWindow::setHidden(bool hidden)
-	{
-		mHidden = hidden;
-		if (!mIsExternal)
-		{
-			if (hidden)
-				ShowWindow(mHWnd, SW_HIDE);
-			else
-				ShowWindow(mHWnd, SW_SHOWNORMAL);
-		}
+	void D3D11RenderWindow::windowMovedOrResized()
+	{
+		if (!mHWnd || IsIconic(mHWnd))
+			return;
+
+		RECT rc;
+		// top and left represent outer window position
+		GetWindowRect(mHWnd, &rc);
+		mTop = rc.top;
+		mLeft = rc.left;
+		// width and height represent drawable area only
+		GetClientRect(mHWnd, &rc);
+		unsigned int width = rc.right - rc.left;
+		unsigned int height = rc.bottom - rc.top;
+
+		if (width == 0) 
+			width = 1;
+		if (height == 0)
+			height = 1;
+
+		if (mWidth == width && mHeight == height)
+			return;
+
+		_resizeSwapChainBuffers(width, height);
 	}
 
-	void D3D11RenderWindow::setFullscreen(bool fullScreen, unsigned int width, unsigned int height)
-	{
-		if (fullScreen != mIsFullScreen || width != mWidth || height != mHeight)
-		{
-			if (fullScreen != mIsFullScreen)
-				mSwitchingFullscreen = true;
-
-			DWORD dwStyle = WS_VISIBLE | WS_CLIPCHILDREN;
-
-			bool oldFullscreen = mIsFullScreen;
-			mIsFullScreen = fullScreen;
-
-			if (fullScreen)
-			{
-				dwStyle |= WS_POPUP;
-				mTop = mLeft = 0;
-				mWidth = width;
-				mHeight = height;
-				// need different ordering here
-
-				if (oldFullscreen)
-				{
-					// was previously fullscreen, just changing the resolution
-					SetWindowPos(mHWnd, HWND_TOPMOST, 0, 0, width, height, SWP_NOACTIVATE);
-				}
-				else
-				{
-					SetWindowPos(mHWnd, HWND_TOPMOST, 0, 0, width, height, SWP_NOACTIVATE);
-					//MoveWindow(mHWnd, mLeft, mTop, mWidth, mHeight, FALSE);
-					SetWindowLong(mHWnd, GWL_STYLE, dwStyle);
-					SetWindowPos(mHWnd, 0, 0,0, 0,0, SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER);
-				}
-			}
-			else
-			{
-				dwStyle |= WS_OVERLAPPEDWINDOW;
-				// Calculate window dimensions required
-				// to get the requested client area
-				RECT rc;
-				SetRect(&rc, 0, 0, width, height);
-				AdjustWindowRect(&rc, dwStyle, false);
-				unsigned int winWidth = rc.right - rc.left;
-				unsigned int winHeight = rc.bottom - rc.top;
-
-				SetWindowLong(mHWnd, GWL_STYLE, dwStyle);
-				SetWindowPos(mHWnd, HWND_NOTOPMOST, 0, 0, winWidth, winHeight,
-					SWP_DRAWFRAME | SWP_FRAMECHANGED | SWP_NOMOVE | SWP_NOACTIVATE);
-				// Note that we also set the position in the restoreLostDevice method
-				// via _finishSwitchingFullScreen
-			}
-
-			mSwapChainDesc.Windowed = !fullScreen;
-			mSwapChainDesc.BufferDesc.RefreshRate.Numerator = 0;
-			mSwapChainDesc.BufferDesc.RefreshRate.Denominator=0;
-			mSwapChainDesc.BufferDesc.Height = height;
-			mSwapChainDesc.BufferDesc.Width = width;
-		}
+	void D3D11RenderWindow::setActive(bool state)
+	{
+		if (mHWnd && mSwapChain)
+		{
+			if (state)
+			{
+				ShowWindow(mHWnd, SW_RESTORE);
+				mSwapChain->SetFullscreenState(mIsFullScreen, nullptr);
+			}
+			else
+			{
+				ShowWindow(mHWnd, SW_SHOWMINIMIZED);
+				mSwapChain->SetFullscreenState(FALSE, nullptr);
+			}
+		}
+
+		RenderWindow::setActive(state);
+	}
+
+	void D3D11RenderWindow::setHidden(bool hidden)
+	{
+		mHidden = hidden;
+		if (!mIsExternal)
+		{
+			if (hidden)
+				ShowWindow(mHWnd, SW_HIDE);
+			else
+				ShowWindow(mHWnd, SW_SHOWNORMAL);
+		}
+	}
+
+	void D3D11RenderWindow::setFullscreen(bool fullScreen, unsigned int width, unsigned int height)
+	{
+		if (fullScreen != mIsFullScreen || width != mWidth || height != mHeight)
+		{
+			if (fullScreen != mIsFullScreen)
+				mSwitchingFullscreen = true;
+
+			DWORD dwStyle = WS_VISIBLE | WS_CLIPCHILDREN;
+
+			bool oldFullscreen = mIsFullScreen;
+			mIsFullScreen = fullScreen;
+
+			if (fullScreen)
+			{
+				dwStyle |= WS_POPUP;
+				mTop = mLeft = 0;
+				mWidth = width;
+				mHeight = height;
+				// need different ordering here
+
+				if (oldFullscreen)
+				{
+					// was previously fullscreen, just changing the resolution
+					SetWindowPos(mHWnd, HWND_TOPMOST, 0, 0, width, height, SWP_NOACTIVATE);
+				}
+				else
+				{
+					SetWindowPos(mHWnd, HWND_TOPMOST, 0, 0, width, height, SWP_NOACTIVATE);
+					//MoveWindow(mHWnd, mLeft, mTop, mWidth, mHeight, FALSE);
+					SetWindowLong(mHWnd, GWL_STYLE, dwStyle);
+					SetWindowPos(mHWnd, 0, 0,0, 0,0, SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER);
+				}
+			}
+			else
+			{
+				dwStyle |= WS_OVERLAPPEDWINDOW;
+				// Calculate window dimensions required
+				// to get the requested client area
+				RECT rc;
+				SetRect(&rc, 0, 0, width, height);
+				AdjustWindowRect(&rc, dwStyle, false);
+				unsigned int winWidth = rc.right - rc.left;
+				unsigned int winHeight = rc.bottom - rc.top;
+
+				SetWindowLong(mHWnd, GWL_STYLE, dwStyle);
+				SetWindowPos(mHWnd, HWND_NOTOPMOST, 0, 0, winWidth, winHeight,
+					SWP_DRAWFRAME | SWP_FRAMECHANGED | SWP_NOMOVE | SWP_NOACTIVATE);
+				// Note that we also set the position in the restoreLostDevice method
+				// via _finishSwitchingFullScreen
+			}
+
+			mSwapChainDesc.Windowed = !fullScreen;
+			mSwapChainDesc.BufferDesc.RefreshRate.Numerator = 0;
+			mSwapChainDesc.BufferDesc.RefreshRate.Denominator=0;
+			mSwapChainDesc.BufferDesc.Height = height;
+			mSwapChainDesc.BufferDesc.Width = width;
+		}
 	} 
 
-	void D3D11RenderWindow::getCustomAttribute( const String& name, void* pData )
-	{
-		// Valid attributes and their equvalent native functions:
-		// D3DDEVICE			: getD3DDevice
-		// WINDOW				: getWindowHandle
-
-		if(name == "WINDOW")
-		{
-			HWND *pWnd = (HWND*)pData;
-			*pWnd = mHWnd;
-			return;
-		}
-
-		if(name == "D3DDEVICE")
-		{
-			ID3D11Device **device = (ID3D11Device **)pData;
-			*device = mDevice.getD3D11Device();
-			return;
-		}
-		else if(name == "isTexture")
-		{
-			bool *b = reinterpret_cast< bool * >( pData );
-			*b = false;
-			return;
-		}
-		else if(name == "ID3D11RenderTargetView")
-		{
-			*static_cast<ID3D11RenderTargetView**>(pData) = mRenderTargetView;
-			return;
-		}
-		else if(name == "ID3D11Texture2D")
-		{
-			ID3D11Texture2D **pBackBuffer = (ID3D11Texture2D**)pData;
-			*pBackBuffer = mBackBuffer;
-			return;
-		}
-		else if(name == "numberOfViews")
-		{
-			unsigned int* n = reinterpret_cast<unsigned int*>(pData);
-			*n = 1;
-			return;
-		}
-		else if(name == "DDBACKBUFFER")
-		{
-			ID3D11Texture2D **ppBackBuffer = (ID3D11Texture2D**) pData;
-			ppBackBuffer[0] = NULL;
-			return;
-		}
-
-		RenderWindow::getCustomAttribute_internal(name, pData);
+	void D3D11RenderWindow::getCustomAttribute( const String& name, void* pData )
+	{
+		// Valid attributes and their equvalent native functions:
+		// D3DDEVICE			: getD3DDevice
+		// WINDOW				: getWindowHandle
+
+		if(name == "WINDOW")
+		{
+			HWND *pWnd = (HWND*)pData;
+			*pWnd = mHWnd;
+			return;
+		}
+
+		if(name == "D3DDEVICE")
+		{
+			ID3D11Device **device = (ID3D11Device **)pData;
+			*device = mDevice.getD3D11Device();
+			return;
+		}
+		else if(name == "isTexture")
+		{
+			bool *b = reinterpret_cast< bool * >( pData );
+			*b = false;
+			return;
+		}
+		else if(name == "ID3D11RenderTargetView")
+		{
+			*static_cast<ID3D11RenderTargetView**>(pData) = mRenderTargetView;
+			return;
+		}
+		else if(name == "ID3D11Texture2D")
+		{
+			ID3D11Texture2D **pBackBuffer = (ID3D11Texture2D**)pData;
+			*pBackBuffer = mBackBuffer;
+			return;
+		}
+		else if(name == "numberOfViews")
+		{
+			unsigned int* n = reinterpret_cast<unsigned int*>(pData);
+			*n = 1;
+			return;
+		}
+		else if(name == "DDBACKBUFFER")
+		{
+			ID3D11Texture2D **ppBackBuffer = (ID3D11Texture2D**) pData;
+			ppBackBuffer[0] = NULL;
+			return;
+		}
+
+		RenderWindow::getCustomAttribute_internal(name, pData);
 	}
 
-	void D3D11RenderWindow::copyContentsToMemory(const PixelData &dst, FrameBuffer buffer)
-	{
-		if(mBackBuffer == nullptr)
-			return;
-
-		// get the backbuffer desc
-		D3D11_TEXTURE2D_DESC BBDesc;
-		mBackBuffer->GetDesc(&BBDesc);
-
-		ID3D11Texture2D *backbuffer = nullptr;
-
-		if(BBDesc.SampleDesc.Quality > 0)
-		{
-			D3D11_TEXTURE2D_DESC desc = BBDesc;
-			desc.Usage = D3D11_USAGE_DEFAULT;
-			desc.CPUAccessFlags = 0;
-			desc.BindFlags = 0;
-			desc.SampleDesc.Quality = 0;
-			desc.SampleDesc.Count = 1;
-
-			HRESULT hr = mDevice.getD3D11Device()->CreateTexture2D(
-				&desc,
-				NULL,
-				&backbuffer);
-
-			if (FAILED(hr) || mDevice.hasError())
-			{
-				String errorDescription = mDevice.getErrorDescription();
-				CM_EXCEPT(RenderingAPIException,
-					"Error creating texture\nError Description:" + errorDescription);
-			}
-
-			mDevice.getImmediateContext()->ResolveSubresource(backbuffer, D3D11CalcSubresource(0, 0, 1), mBackBuffer, D3D11CalcSubresource(0, 0, 1), desc.Format);
-		}
-
-
-		// change the parameters of the texture so we can read it
-		BBDesc.Usage = D3D11_USAGE_STAGING;
-		BBDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
-		BBDesc.BindFlags = 0;
-		BBDesc.SampleDesc.Quality = 0;
-		BBDesc.SampleDesc.Count = 1;
-
-		// create a temp buffer to copy to
-		ID3D11Texture2D * pTempTexture2D;
-		HRESULT hr = mDevice.getD3D11Device()->CreateTexture2D(
-			&BBDesc,
-			NULL,
-			&pTempTexture2D);
-
-		if (FAILED(hr) || mDevice.hasError())
-		{
-			String errorDescription = mDevice.getErrorDescription();
-			CM_EXCEPT(RenderingAPIException,
-				"Error creating texture\nError Description:" + errorDescription);
-		}
-		// copy the back buffer
-		mDevice.getImmediateContext()->CopyResource(pTempTexture2D, backbuffer != NULL ? backbuffer : mBackBuffer);
-
-		// map the copied texture
-		D3D11_MAPPED_SUBRESOURCE mappedTex2D;
-		mDevice.getImmediateContext()->Map(pTempTexture2D, 0,D3D11_MAP_READ, 0, &mappedTex2D);
-
-		// copy the the texture to the dest
-		PixelUtil::bulkPixelConversion(PixelData(mWidth, mHeight, 1, PF_A8B8G8R8, mappedTex2D.pData), dst);
-
-		// unmap the temp buffer
-		mDevice.getImmediateContext()->Unmap(pTempTexture2D, 0);
-
-		// Release the temp buffer
-		SAFE_RELEASE(pTempTexture2D);
-		SAFE_RELEASE(backbuffer);
+	void D3D11RenderWindow::copyContentsToMemory(const PixelData &dst, FrameBuffer buffer)
+	{
+		if(mBackBuffer == nullptr)
+			return;
+
+		// get the backbuffer desc
+		D3D11_TEXTURE2D_DESC BBDesc;
+		mBackBuffer->GetDesc(&BBDesc);
+
+		ID3D11Texture2D *backbuffer = nullptr;
+
+		if(BBDesc.SampleDesc.Quality > 0)
+		{
+			D3D11_TEXTURE2D_DESC desc = BBDesc;
+			desc.Usage = D3D11_USAGE_DEFAULT;
+			desc.CPUAccessFlags = 0;
+			desc.BindFlags = 0;
+			desc.SampleDesc.Quality = 0;
+			desc.SampleDesc.Count = 1;
+
+			HRESULT hr = mDevice.getD3D11Device()->CreateTexture2D(
+				&desc,
+				NULL,
+				&backbuffer);
+
+			if (FAILED(hr) || mDevice.hasError())
+			{
+				String errorDescription = mDevice.getErrorDescription();
+				CM_EXCEPT(RenderingAPIException,
+					"Error creating texture\nError Description:" + errorDescription);
+			}
+
+			mDevice.getImmediateContext()->ResolveSubresource(backbuffer, D3D11CalcSubresource(0, 0, 1), mBackBuffer, D3D11CalcSubresource(0, 0, 1), desc.Format);
+		}
+
+
+		// change the parameters of the texture so we can read it
+		BBDesc.Usage = D3D11_USAGE_STAGING;
+		BBDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
+		BBDesc.BindFlags = 0;
+		BBDesc.SampleDesc.Quality = 0;
+		BBDesc.SampleDesc.Count = 1;
+
+		// create a temp buffer to copy to
+		ID3D11Texture2D * pTempTexture2D;
+		HRESULT hr = mDevice.getD3D11Device()->CreateTexture2D(
+			&BBDesc,
+			NULL,
+			&pTempTexture2D);
+
+		if (FAILED(hr) || mDevice.hasError())
+		{
+			String errorDescription = mDevice.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException,
+				"Error creating texture\nError Description:" + errorDescription);
+		}
+		// copy the back buffer
+		mDevice.getImmediateContext()->CopyResource(pTempTexture2D, backbuffer != NULL ? backbuffer : mBackBuffer);
+
+		// map the copied texture
+		D3D11_MAPPED_SUBRESOURCE mappedTex2D;
+		mDevice.getImmediateContext()->Map(pTempTexture2D, 0,D3D11_MAP_READ, 0, &mappedTex2D);
+
+		// copy the the texture to the dest
+		PixelUtil::bulkPixelConversion(PixelData(mWidth, mHeight, 1, PF_A8B8G8R8, mappedTex2D.pData), dst);
+
+		// unmap the temp buffer
+		mDevice.getImmediateContext()->Unmap(pTempTexture2D, 0);
+
+		// Release the temp buffer
+		SAFE_RELEASE(pTempTexture2D);
+		SAFE_RELEASE(backbuffer);
 	}
 
 	void D3D11RenderWindow::_createSwapChain()
 	{
-		ZeroMemory(&mSwapChainDesc, sizeof(DXGI_SWAP_CHAIN_DESC));
-
-		// get the dxgi device
+		ZeroMemory(&mSwapChainDesc, sizeof(DXGI_SWAP_CHAIN_DESC));
+
+		// get the dxgi device
 		IDXGIDevice* pDXGIDevice = _queryDxgiDevice();
 
-		ZeroMemory(&mSwapChainDesc, sizeof(DXGI_SWAP_CHAIN_DESC));
-		DXGI_FORMAT format = DXGI_FORMAT_R8G8B8A8_UNORM;
-		mSwapChainDesc.OutputWindow			= mHWnd;
-		mSwapChainDesc.BufferDesc.Width		= mWidth;
-		mSwapChainDesc.BufferDesc.Height	= mHeight;
-		mSwapChainDesc.BufferDesc.Format	= format;
-		mSwapChainDesc.BufferDesc.RefreshRate.Numerator=0;
-		mSwapChainDesc.BufferDesc.RefreshRate.Denominator = 0;
-
-		mSwapChainDesc.BufferDesc.ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED;
-		mSwapChainDesc.BufferDesc.Scaling = DXGI_MODE_SCALING_UNSPECIFIED;
-		mSwapChainDesc.Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH ;
-
-		// triple buffer if VSync is on
-		mSwapChainDesc.BufferUsage			= DXGI_USAGE_RENDER_TARGET_OUTPUT;
-		mSwapChainDesc.BufferCount			= mVSync ? 2 : 1;
-		mSwapChainDesc.SwapEffect			= DXGI_SWAP_EFFECT_DISCARD ;
-
-		mSwapChainDesc.OutputWindow 		= mHWnd;
-		mSwapChainDesc.Windowed				= !mIsFullScreen;
-
-		D3D11RenderSystem* rs = static_cast<D3D11RenderSystem*>(RenderSystem::instancePtr());
-		rs->determineFSAASettings(mFSAA, mFSAAHint, format, &mFSAAType);
-		mSwapChainDesc.SampleDesc.Count = mFSAAType.Count;
-		mSwapChainDesc.SampleDesc.Quality = mFSAAType.Quality;
-
-		HRESULT hr;
-
-		// Create swap chain			
-		hr = mDXGIFactory->CreateSwapChain(pDXGIDevice, &mSwapChainDesc, &mSwapChain);
-
-		if (FAILED(hr))
-		{
-			// Try a second time, may fail the first time due to back buffer count,
-			// which will be corrected by the runtime
-			hr = mDXGIFactory->CreateSwapChain(pDXGIDevice, &mSwapChainDesc, &mSwapChain);
-		}
-
-		SAFE_RELEASE(pDXGIDevice);
-
-		if (FAILED(hr))
+		ZeroMemory(&mSwapChainDesc, sizeof(DXGI_SWAP_CHAIN_DESC));
+		DXGI_FORMAT format = DXGI_FORMAT_R8G8B8A8_UNORM;
+		mSwapChainDesc.OutputWindow			= mHWnd;
+		mSwapChainDesc.BufferDesc.Width		= mWidth;
+		mSwapChainDesc.BufferDesc.Height	= mHeight;
+		mSwapChainDesc.BufferDesc.Format	= format;
+		mSwapChainDesc.BufferDesc.RefreshRate.Numerator=0;
+		mSwapChainDesc.BufferDesc.RefreshRate.Denominator = 0;
+
+		mSwapChainDesc.BufferDesc.ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED;
+		mSwapChainDesc.BufferDesc.Scaling = DXGI_MODE_SCALING_UNSPECIFIED;
+		mSwapChainDesc.Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH ;
+
+		// triple buffer if VSync is on
+		mSwapChainDesc.BufferUsage			= DXGI_USAGE_RENDER_TARGET_OUTPUT;
+		mSwapChainDesc.BufferCount			= mVSync ? 2 : 1;
+		mSwapChainDesc.SwapEffect			= DXGI_SWAP_EFFECT_DISCARD ;
+
+		mSwapChainDesc.OutputWindow 		= mHWnd;
+		mSwapChainDesc.Windowed				= !mIsFullScreen;
+
+		D3D11RenderSystem* rs = static_cast<D3D11RenderSystem*>(RenderSystem::instancePtr());
+		rs->determineFSAASettings(mFSAA, mFSAAHint, format, &mFSAAType);
+		mSwapChainDesc.SampleDesc.Count = mFSAAType.Count;
+		mSwapChainDesc.SampleDesc.Quality = mFSAAType.Quality;
+
+		HRESULT hr;
+
+		// Create swap chain			
+		hr = mDXGIFactory->CreateSwapChain(pDXGIDevice, &mSwapChainDesc, &mSwapChain);
+
+		if (FAILED(hr))
+		{
+			// Try a second time, may fail the first time due to back buffer count,
+			// which will be corrected by the runtime
+			hr = mDXGIFactory->CreateSwapChain(pDXGIDevice, &mSwapChainDesc, &mSwapChain);
+		}
+
+		SAFE_RELEASE(pDXGIDevice);
+
+		if (FAILED(hr))
 			CM_EXCEPT(RenderingAPIException, "Unable to create swap chain");
 	}
 
-	void D3D11RenderWindow::_createSizeDependedD3DResources()
-	{
-		// obtain back buffer
-		SAFE_RELEASE(mBackBuffer);
-
-		HRESULT hr = mSwapChain->GetBuffer(0,  __uuidof( ID3D11Texture2D ), (LPVOID*)&mBackBuffer);
-		if( FAILED(hr) )
-			CM_EXCEPT(RenderingAPIException, "Unable to Get Back Buffer for swap chain");
-
-		// create all other size depended resources
-		assert(mBackBuffer && !mRenderTargetView && !mDepthStencilView);
-
-		// get the backbuffer desc
-		D3D11_TEXTURE2D_DESC BBDesc;
-		mBackBuffer->GetDesc(&BBDesc);
-
-		// create the render target view
-		D3D11_RENDER_TARGET_VIEW_DESC RTVDesc;
-		ZeroMemory( &RTVDesc, sizeof(RTVDesc) );
-
-		RTVDesc.Format = BBDesc.Format;
-		RTVDesc.ViewDimension = mFSAA ? D3D11_RTV_DIMENSION_TEXTURE2DMS : D3D11_RTV_DIMENSION_TEXTURE2D;
-		RTVDesc.Texture2D.MipSlice = 0;
-		hr = mDevice.getD3D11Device()->CreateRenderTargetView(mBackBuffer, &RTVDesc, &mRenderTargetView);
-
-		if( FAILED(hr) )
-		{
-			String errorDescription = mDevice.getErrorDescription();
-			CM_EXCEPT(RenderingAPIException, "Unable to create rendertagert view\nError Description:" + errorDescription);
-		}
-
-		mDepthStencilBuffer = TextureManager::instance().createDepthStencilBuffer(32, BBDesc.Width, BBDesc.Height, mFSAA, mFSAAHint);
-
-		//if(mDepthBufferPoolId != DepthStencilBuffer::POOL_NO_DEPTH)
-		//{
-		//	// Create depth stencil texture
-		//	ID3D11Texture2D* pDepthStencil = NULL;
-		//	D3D11_TEXTURE2D_DESC descDepth;
-
-		//	descDepth.Width = BBDesc.Width;
-		//	descDepth.Height = BBDesc.Height;
-		//	descDepth.MipLevels = 1;
-		//	descDepth.ArraySize = 1;
-		//	descDepth.Format = DXGI_FORMAT_D24_UNORM_S8_UINT;
-		//	descDepth.SampleDesc.Count = mFSAAType.Count;
-		//	descDepth.SampleDesc.Quality = mFSAAType.Quality;
-		//	descDepth.Usage = D3D11_USAGE_DEFAULT;
-		//	descDepth.BindFlags = D3D11_BIND_DEPTH_STENCIL;
-		//	descDepth.CPUAccessFlags = 0;
-		//	descDepth.MiscFlags = 0;
-
-		//	hr = mDevice.getD3D11Device()->CreateTexture2D(&descDepth, NULL, &pDepthStencil);
-		//	if( FAILED(hr) || mDevice.hasError())
-		//	{
-		//		String errorDescription = mDevice.getErrorDescription(hr);
-		//		CM_EXCEPT(RenderingAPIException, "Unable to create depth texture\nError Description:" + errorDescription);
-		//	}
-
-		//	// Create the depth stencil view
-		//	D3D11_DEPTH_STENCIL_VIEW_DESC descDSV;
-		//	ZeroMemory( &descDSV, sizeof(D3D11_DEPTH_STENCIL_VIEW_DESC) );
-
-		//	descDSV.Format =  descDepth.Format;
-		//	descDSV.ViewDimension = mFSAA ? D3D11_DSV_DIMENSION_TEXTURE2DMS : D3D11_DSV_DIMENSION_TEXTURE2D;
-		//	descDSV.Texture2D.MipSlice = 0;
-		//	hr = mDevice.getD3D11Device()->CreateDepthStencilView(pDepthStencil, &descDSV, &mDepthStencilView);
-
-		//	SAFE_RELEASE(pDepthStencil);
-
-		//	if( FAILED(hr) )
-		//	{
-		//		String errorDescription = mDevice.getErrorDescription();
-		//		CM_EXCEPT(RenderingAPIException, 
-		//			"Unable to create depth stencil view\nError Description:" + errorDescription);
-		//	}
-
-		//	D3D11RenderSystem* rsys = static_cast<D3D11RenderSystem*>(RenderSystem::instancePtr());
-		//	DepthStencilBuffer *depthBuf = rsys->_addManualDepthBuffer(mDepthStencilView, mWidth, mHeight, mFSAAType.Count, mFSAAType.Quality);
-
-		//	//Don't forget we want this window to use _this_ depth buffer
-		//	this->attachDepthBuffer(depthBuf);
-		//} 
-	}
-
-	void D3D11RenderWindow::_destroySizeDependedD3DResources()
-	{
-		SAFE_RELEASE(mBackBuffer);
-		SAFE_RELEASE(mRenderTargetView);
-
-		mDepthStencilBuffer = nullptr;
-
-		SAFE_RELEASE(mDepthStencilView);
-	}
-
-	void D3D11RenderWindow::_resizeSwapChainBuffers(unsigned width, unsigned height)
-	{
-		_destroySizeDependedD3DResources();
-
-		// width and height can be zero to autodetect size, therefore do not rely on them
-		UINT Flags = mIsFullScreen ? DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH : 0;
-		mSwapChain->ResizeBuffers(mSwapChainDesc.BufferCount, width, height, mSwapChainDesc.BufferDesc.Format, Flags);
-		mSwapChain->GetDesc(&mSwapChainDesc);
-		mWidth = mSwapChainDesc.BufferDesc.Width;
-		mHeight = mSwapChainDesc.BufferDesc.Height;
-		mIsFullScreen = (0 == mSwapChainDesc.Windowed); // Alt-Enter together with SetWindowAssociation() can change this state
-
-		_createSizeDependedD3DResources();
-
-		mDevice.getImmediateContext()->OMSetRenderTargets(0, 0, 0);
-		// Additional swap chains need their own depth buffer
-		// to support resizing them
-
-		HRESULT hr = mSwapChain->GetBuffer( 0,  __uuidof( ID3D11Texture2D ), (LPVOID*)&mBackBuffer  );
-		if( FAILED(hr) )
-		{
-			CM_EXCEPT(RenderingAPIException, 
-				"Unable to Get Back Buffer for swap chain");
-		}
-
-		// get the backbuffer desc
-		D3D11_TEXTURE2D_DESC BBDesc;
-		mBackBuffer->GetDesc(&BBDesc);
-
-		// create the render target view
-		D3D11_RENDER_TARGET_VIEW_DESC RTVDesc;
-		ZeroMemory( &RTVDesc, sizeof(RTVDesc) );
-
-		RTVDesc.Format = BBDesc.Format;
-		RTVDesc.ViewDimension = mFSAA ? D3D11_RTV_DIMENSION_TEXTURE2DMS : D3D11_RTV_DIMENSION_TEXTURE2D;
-		RTVDesc.Texture2D.MipSlice = 0;
-		hr = mDevice.getD3D11Device()->CreateRenderTargetView(mBackBuffer, &RTVDesc, &mRenderTargetView);
-
-		if(FAILED(hr))
-		{
-			String errorDescription = mDevice.getErrorDescription();
-			CM_EXCEPT(RenderingAPIException, 
-				"Unable to create rendertagert view\nError Description:" + errorDescription);
-		}
-	}
-
-	IDXGIDevice* D3D11RenderWindow::_queryDxgiDevice()
-	{
-		if (mDevice.getD3D11Device() == nullptr)
-		{
-			CM_EXCEPT(RenderingAPIException, "D3D11Device is NULL!");
-		}
-
-		IDXGIDevice* pDXGIDevice = nullptr;
-		HRESULT hr = mDevice.getD3D11Device()->QueryInterface(__uuidof(IDXGIDevice), (void**)&pDXGIDevice);
-		if(FAILED(hr))
-			CM_EXCEPT(RenderingAPIException, "Unable to query a DXGIDevice");
-
-		return pDXGIDevice;
-	}
-
-	void D3D11RenderWindow::_finishSwitchingFullscreen()
-	{
-		if(mIsFullScreen)
-		{
-			// Need to reset the region on the window sometimes, when the 
-			// windowed mode was constrained by desktop 
-			HRGN hRgn = CreateRectRgn(0, 0, mSwapChainDesc.BufferDesc.Width, mSwapChainDesc.BufferDesc.Height);
-			SetWindowRgn(mHWnd, hRgn, FALSE);
-		}
-		else
-		{
-			// When switching back to windowed mode, need to reset window size 
-			// after device has been restored
-			RECT rc;
-			SetRect(&rc, 0, 0, mSwapChainDesc.BufferDesc.Width, mSwapChainDesc.BufferDesc.Height);
-			AdjustWindowRect(&rc, GetWindowLong(mHWnd, GWL_STYLE), false);
-			unsigned int winWidth = rc.right - rc.left;
-			unsigned int winHeight = rc.bottom - rc.top;
-			int screenw = GetSystemMetrics(SM_CXSCREEN);
-			int screenh = GetSystemMetrics(SM_CYSCREEN);
-			int left = (screenw - winWidth) / 2;
-			int top = (screenh - winHeight) / 2;
-			SetWindowPos(mHWnd, HWND_NOTOPMOST, left, top, winWidth, winHeight,
-				SWP_DRAWFRAME | SWP_FRAMECHANGED | SWP_NOACTIVATE);
-		}
-
-		mSwapChain->SetFullscreenState(mIsFullScreen, NULL);
-		mSwitchingFullscreen = false;
+	void D3D11RenderWindow::_createSizeDependedD3DResources()
+	{
+		// obtain back buffer
+		SAFE_RELEASE(mBackBuffer);
+
+		HRESULT hr = mSwapChain->GetBuffer(0,  __uuidof( ID3D11Texture2D ), (LPVOID*)&mBackBuffer);
+		if( FAILED(hr) )
+			CM_EXCEPT(RenderingAPIException, "Unable to Get Back Buffer for swap chain");
+
+		// create all other size depended resources
+		assert(mBackBuffer && !mRenderTargetView && !mDepthStencilView);
+
+		// get the backbuffer desc
+		D3D11_TEXTURE2D_DESC BBDesc;
+		mBackBuffer->GetDesc(&BBDesc);
+
+		// create the render target view
+		D3D11_RENDER_TARGET_VIEW_DESC RTVDesc;
+		ZeroMemory( &RTVDesc, sizeof(RTVDesc) );
+
+		RTVDesc.Format = BBDesc.Format;
+		RTVDesc.ViewDimension = mFSAA ? D3D11_RTV_DIMENSION_TEXTURE2DMS : D3D11_RTV_DIMENSION_TEXTURE2D;
+		RTVDesc.Texture2D.MipSlice = 0;
+		hr = mDevice.getD3D11Device()->CreateRenderTargetView(mBackBuffer, &RTVDesc, &mRenderTargetView);
+
+		if( FAILED(hr) )
+		{
+			String errorDescription = mDevice.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "Unable to create rendertagert view\nError Description:" + errorDescription);
+		}
+
+		mDepthStencilBuffer = TextureManager::instance().createDepthStencilBuffer(32, BBDesc.Width, BBDesc.Height, mFSAA, mFSAAHint);
+
+		//if(mDepthBufferPoolId != DepthStencilBuffer::POOL_NO_DEPTH)
+		//{
+		//	// Create depth stencil texture
+		//	ID3D11Texture2D* pDepthStencil = NULL;
+		//	D3D11_TEXTURE2D_DESC descDepth;
+
+		//	descDepth.Width = BBDesc.Width;
+		//	descDepth.Height = BBDesc.Height;
+		//	descDepth.MipLevels = 1;
+		//	descDepth.ArraySize = 1;
+		//	descDepth.Format = DXGI_FORMAT_D24_UNORM_S8_UINT;
+		//	descDepth.SampleDesc.Count = mFSAAType.Count;
+		//	descDepth.SampleDesc.Quality = mFSAAType.Quality;
+		//	descDepth.Usage = D3D11_USAGE_DEFAULT;
+		//	descDepth.BindFlags = D3D11_BIND_DEPTH_STENCIL;
+		//	descDepth.CPUAccessFlags = 0;
+		//	descDepth.MiscFlags = 0;
+
+		//	hr = mDevice.getD3D11Device()->CreateTexture2D(&descDepth, NULL, &pDepthStencil);
+		//	if( FAILED(hr) || mDevice.hasError())
+		//	{
+		//		String errorDescription = mDevice.getErrorDescription(hr);
+		//		CM_EXCEPT(RenderingAPIException, "Unable to create depth texture\nError Description:" + errorDescription);
+		//	}
+
+		//	// Create the depth stencil view
+		//	D3D11_DEPTH_STENCIL_VIEW_DESC descDSV;
+		//	ZeroMemory( &descDSV, sizeof(D3D11_DEPTH_STENCIL_VIEW_DESC) );
+
+		//	descDSV.Format =  descDepth.Format;
+		//	descDSV.ViewDimension = mFSAA ? D3D11_DSV_DIMENSION_TEXTURE2DMS : D3D11_DSV_DIMENSION_TEXTURE2D;
+		//	descDSV.Texture2D.MipSlice = 0;
+		//	hr = mDevice.getD3D11Device()->CreateDepthStencilView(pDepthStencil, &descDSV, &mDepthStencilView);
+
+		//	SAFE_RELEASE(pDepthStencil);
+
+		//	if( FAILED(hr) )
+		//	{
+		//		String errorDescription = mDevice.getErrorDescription();
+		//		CM_EXCEPT(RenderingAPIException, 
+		//			"Unable to create depth stencil view\nError Description:" + errorDescription);
+		//	}
+
+		//	D3D11RenderSystem* rsys = static_cast<D3D11RenderSystem*>(RenderSystem::instancePtr());
+		//	DepthStencilBuffer *depthBuf = rsys->_addManualDepthBuffer(mDepthStencilView, mWidth, mHeight, mFSAAType.Count, mFSAAType.Quality);
+
+		//	//Don't forget we want this window to use _this_ depth buffer
+		//	this->attachDepthBuffer(depthBuf);
+		//} 
+	}
+
+	void D3D11RenderWindow::_destroySizeDependedD3DResources()
+	{
+		SAFE_RELEASE(mBackBuffer);
+		SAFE_RELEASE(mRenderTargetView);
+
+		mDepthStencilBuffer = nullptr;
+
+		SAFE_RELEASE(mDepthStencilView);
+	}
+
+	void D3D11RenderWindow::_resizeSwapChainBuffers(unsigned width, unsigned height)
+	{
+		_destroySizeDependedD3DResources();
+
+		// width and height can be zero to autodetect size, therefore do not rely on them
+		UINT Flags = mIsFullScreen ? DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH : 0;
+		mSwapChain->ResizeBuffers(mSwapChainDesc.BufferCount, width, height, mSwapChainDesc.BufferDesc.Format, Flags);
+		mSwapChain->GetDesc(&mSwapChainDesc);
+		mWidth = mSwapChainDesc.BufferDesc.Width;
+		mHeight = mSwapChainDesc.BufferDesc.Height;
+		mIsFullScreen = (0 == mSwapChainDesc.Windowed); // Alt-Enter together with SetWindowAssociation() can change this state
+
+		_createSizeDependedD3DResources();
+
+		mDevice.getImmediateContext()->OMSetRenderTargets(0, 0, 0);
+		// Additional swap chains need their own depth buffer
+		// to support resizing them
+
+		HRESULT hr = mSwapChain->GetBuffer( 0,  __uuidof( ID3D11Texture2D ), (LPVOID*)&mBackBuffer  );
+		if( FAILED(hr) )
+		{
+			CM_EXCEPT(RenderingAPIException, 
+				"Unable to Get Back Buffer for swap chain");
+		}
+
+		// get the backbuffer desc
+		D3D11_TEXTURE2D_DESC BBDesc;
+		mBackBuffer->GetDesc(&BBDesc);
+
+		// create the render target view
+		D3D11_RENDER_TARGET_VIEW_DESC RTVDesc;
+		ZeroMemory( &RTVDesc, sizeof(RTVDesc) );
+
+		RTVDesc.Format = BBDesc.Format;
+		RTVDesc.ViewDimension = mFSAA ? D3D11_RTV_DIMENSION_TEXTURE2DMS : D3D11_RTV_DIMENSION_TEXTURE2D;
+		RTVDesc.Texture2D.MipSlice = 0;
+		hr = mDevice.getD3D11Device()->CreateRenderTargetView(mBackBuffer, &RTVDesc, &mRenderTargetView);
+
+		if(FAILED(hr))
+		{
+			String errorDescription = mDevice.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, 
+				"Unable to create rendertagert view\nError Description:" + errorDescription);
+		}
 	}
 
-	bool D3D11RenderWindow::_checkMultiSampleQuality(UINT SampleCount, UINT *outQuality, DXGI_FORMAT format)
-	{
-		if (SUCCEEDED(mDevice.getD3D11Device()->CheckMultisampleQualityLevels(format, SampleCount, outQuality)))
-			return true;
-		else
-			return false;
+	IDXGIDevice* D3D11RenderWindow::_queryDxgiDevice()
+	{
+		if (mDevice.getD3D11Device() == nullptr)
+		{
+			CM_EXCEPT(RenderingAPIException, "D3D11Device is NULL!");
+		}
+
+		IDXGIDevice* pDXGIDevice = nullptr;
+		HRESULT hr = mDevice.getD3D11Device()->QueryInterface(__uuidof(IDXGIDevice), (void**)&pDXGIDevice);
+		if(FAILED(hr))
+			CM_EXCEPT(RenderingAPIException, "Unable to query a DXGIDevice");
+
+		return pDXGIDevice;
+	}
+
+	void D3D11RenderWindow::_finishSwitchingFullscreen()
+	{
+		if(mIsFullScreen)
+		{
+			// Need to reset the region on the window sometimes, when the 
+			// windowed mode was constrained by desktop 
+			HRGN hRgn = CreateRectRgn(0, 0, mSwapChainDesc.BufferDesc.Width, mSwapChainDesc.BufferDesc.Height);
+			SetWindowRgn(mHWnd, hRgn, FALSE);
+		}
+		else
+		{
+			// When switching back to windowed mode, need to reset window size 
+			// after device has been restored
+			RECT rc;
+			SetRect(&rc, 0, 0, mSwapChainDesc.BufferDesc.Width, mSwapChainDesc.BufferDesc.Height);
+			AdjustWindowRect(&rc, GetWindowLong(mHWnd, GWL_STYLE), false);
+			unsigned int winWidth = rc.right - rc.left;
+			unsigned int winHeight = rc.bottom - rc.top;
+			int screenw = GetSystemMetrics(SM_CXSCREEN);
+			int screenh = GetSystemMetrics(SM_CYSCREEN);
+			int left = (screenw - winWidth) / 2;
+			int top = (screenh - winHeight) / 2;
+			SetWindowPos(mHWnd, HWND_NOTOPMOST, left, top, winWidth, winHeight,
+				SWP_DRAWFRAME | SWP_FRAMECHANGED | SWP_NOACTIVATE);
+		}
+
+		mSwapChain->SetFullscreenState(mIsFullScreen, NULL);
+		mSwitchingFullscreen = false;
+	}
+
+	bool D3D11RenderWindow::_checkMultiSampleQuality(UINT SampleCount, UINT *outQuality, DXGI_FORMAT format)
+	{
+		if (SUCCEEDED(mDevice.getD3D11Device()->CheckMultisampleQualityLevels(format, SampleCount, outQuality)))
+			return true;
+		else
+			return false;
 	}
 }

+ 584 - 0
CamelotD3D11RenderSystem/Source/CmD3D11Texture.cpp

@@ -0,0 +1,584 @@
+#include "CmD3D11Texture.h"
+#include "CmD3D11Mappings.h"
+#include "CmD3D11Device.h"
+#include "CmD3D11RenderSystem.h"
+#include "CmException.h"
+#include "CmAsyncOp.h"
+
+#if CM_DEBUG_MODE
+#define THROW_IF_NOT_RENDER_THREAD throwIfNotRenderThread();
+#else
+#define THROW_IF_NOT_RENDER_THREAD 
+#endif
+
+namespace CamelotEngine
+{
+	D3D11Texture::D3D11Texture()
+		: m1DTex(nullptr)
+		, m2DTex(nullptr)
+		, m3DTex(nullptr)
+		, mTex(nullptr)
+		, mShaderResourceView(nullptr)
+		, mStagingBuffer(nullptr)
+		, mLockedSubresourceIdx(-1)
+		, mLockedForReading(false)
+		, mStaticBuffer(nullptr)
+	{
+		ZeroMemory(&mSRVDesc, sizeof(D3D11_SHADER_RESOURCE_VIEW_DESC));
+	}
+
+	void D3D11Texture::setRawPixels_internal(const PixelData& data, UINT32 face, UINT32 mip)
+	{
+		THROW_IF_NOT_RENDER_THREAD
+
+		if(mip < 0 || mip > mNumMipmaps)
+			CM_EXCEPT(InvalidParametersException, "Invalid mip level: " + toString(mip) + ". Min is 0, max is " + toString(mNumMipmaps));
+
+		if(face < 0 || face > getNumFaces())
+			CM_EXCEPT(InvalidParametersException, "Invalid face index: " + toString(face) + ". Min is 0, max is " + toString(getNumFaces()));
+
+		if(mFormat != data.format)
+			CM_EXCEPT(InvalidParametersException, "Provided PixelData has invalid format. Needed: " + toString(mFormat) + ". Got: " + toString(data.format));
+
+		if(mWidth != data.getWidth() || mHeight != data.getHeight() || mDepth != data.getDepth())
+		{
+			CM_EXCEPT(InvalidParametersException, "Provided PixelData size doesn't match the texture size." \
+				" Width: " + toString(mWidth) + "/" + toString(data.getWidth()) + 
+				" Height: " + toString(mHeight) + "/" + toString(data.getHeight()) + 
+				" Depth: " + toString(mDepth) + "/" + toString(data.getDepth()));
+		}
+
+		PixelData myData = lock(HBL_WRITE_ONLY_DISCARD, mip, face);
+		memcpy(myData.data, data.data, data.getConsecutiveSize());
+		unlock();
+	}
+
+	void D3D11Texture::getRawPixels_internal(UINT32 face, UINT32 mip, AsyncOp& op)
+	{
+		THROW_IF_NOT_RENDER_THREAD;
+
+		if(mip < 0 || mip > mNumMipmaps)
+			CM_EXCEPT(InvalidParametersException, "Invalid mip level: " + toString(mip) + ". Min is 0, max is " + toString(mNumMipmaps));
+
+		if(face < 0 || mip > getNumFaces())
+			CM_EXCEPT(InvalidParametersException, "Invalid face index: " + toString(face) + ". Min is 0, max is " + toString(getNumFaces()));
+
+		UINT32 numMips = getNumMipmaps();
+
+		UINT32 totalSize = 0;
+		UINT32 width = getWidth();
+		UINT32 height = getHeight();
+		UINT32 depth = getDepth();
+
+		for(UINT32 j = 0; j <= mip; j++)
+		{
+			totalSize = PixelUtil::getMemorySize(width, height, depth, mFormat);
+
+			if(width != 1) width /= 2;
+			if(height != 1) height /= 2;
+			if(depth != 1) depth /= 2;
+		}
+
+		UINT8* buffer = new UINT8[totalSize]; 
+		PixelDataPtr dst(new PixelData(width, height, depth, getFormat(), buffer, true));
+
+		PixelData myData = lock(HBL_READ_ONLY, mip, face);
+
+#if CM_DEBUG_MODE
+		if(dst->getConsecutiveSize() != myData.getConsecutiveSize())
+		{
+			unlock();
+			CM_EXCEPT(InternalErrorException, "Buffer sizes don't match");
+		}
+#endif
+
+		memcpy(dst->data, myData.data, dst->getConsecutiveSize());
+		unlock();
+
+		op.completeOperation(dst);
+	}
+
+	void D3D11Texture::copy_internal(TexturePtr& target)
+	{
+		if (target->getUsage() != this->getUsage() ||
+			target->getTextureType() != this->getTextureType())
+		{
+			CM_EXCEPT(InvalidParametersException, "Source and destination textures must be of same type and must have the same usage and type.");
+		}
+
+		if(getWidth() != target->getWidth() || getHeight() != target->getHeight() || getDepth() != target->getDepth())
+		{
+			CM_EXCEPT(InvalidParametersException, "Texture sizes don't match." \
+				" Width: " + toString(getWidth()) + "/" + toString(target->getWidth()) + 
+				" Height: " + toString(getHeight()) + "/" + toString(target->getHeight()) + 
+				" Depth: " + toString(getDepth()) + "/" + toString(target->getDepth()));
+		}
+
+		if(getNumFaces() != target->getNumFaces())
+		{
+			CM_EXCEPT(InvalidParametersException, "Number of texture faces doesn't match." \
+				" Num faces: " + toString(getNumFaces()) + "/" + toString(target->getNumFaces()));
+		}
+
+		if(getNumMipmaps() != target->getNumMipmaps())
+		{
+			CM_EXCEPT(InvalidParametersException, "Number of mipmaps doesn't match." \
+				" Num mipmaps: " + toString(getNumMipmaps()) + "/" + toString(target->getNumMipmaps()));
+		}
+
+		// get the target
+		D3D11Texture* other = static_cast<D3D11Texture*>(target.get());
+
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		device.getImmediateContext()->CopyResource(other->getDX11Resource(), mTex);
+
+		if (device.hasError())
+		{
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "D3D11 device cannot copy resource\nError Description:" + errorDescription);
+		}
+	}
+
+	PixelData D3D11Texture::lock(LockOptions options, UINT32 mipLevel, UINT32 face)
+	{
+		UINT32 mipWidth = mipLevel >> mWidth;
+		UINT32 mipHeight = mipLevel >> mHeight;
+		UINT32 mipDepth = mipLevel >> mDepth;
+
+		PixelData lockedArea(mipWidth, mipHeight, mipDepth, mFormat);
+
+		D3D11_MAP flags = D3D11Mappings::_getLockOptions(options);
+		switch(options)
+		{
+		case HBL_WRITE_ONLY_NO_OVERWRITE:
+			flags = D3D11_MAP_WRITE_NO_OVERWRITE;
+			break;
+		case HBL_READ_WRITE:
+			flags = D3D11_MAP_READ_WRITE;
+			break;
+		case HBL_WRITE_ONLY_DISCARD:
+			flags = D3D11_MAP_WRITE_DISCARD;
+			break;
+		case HBL_READ_ONLY:
+			flags = D3D11_MAP_READ;
+			break;
+		case HBL_WRITE_ONLY:
+			flags = D3D11_MAP_WRITE;
+			break;
+		default: 
+			break;
+		};
+
+		if(flags == D3D11_MAP_READ || flags == D3D11_MAP_READ_WRITE)
+		{
+			lockedArea.data = _mapstagingbuffer(flags, face, mipLevel);
+			mLockedForReading = true;
+		}
+		else
+		{
+			if(mUsage == TU_DYNAMIC)
+				lockedArea.data = _map(mTex, flags, face, mipLevel);
+			else
+				lockedArea.data = _mapstaticbuffer(lockedArea, mipLevel, face);
+
+			mLockedForReading = false;
+		}
+
+		return lockedArea;
+	}
+
+	void D3D11Texture::unlock()
+	{
+		if(mLockedForReading)
+			_unmapstagingbuffer();
+		else
+			_unmap(mTex);
+	}
+
+	void D3D11Texture::initialize_internal()
+	{
+		THROW_IF_NOT_RENDER_THREAD
+
+		createInternalResources();
+
+		Resource::initialize_internal();
+	}
+
+	void D3D11Texture::createInternalResourcesImpl()
+	{
+		// load based on tex.type
+		switch (getTextureType())
+		{
+		case TEX_TYPE_1D:
+			_create1DTex();
+			break;
+		case TEX_TYPE_2D:
+		case TEX_TYPE_CUBE_MAP:
+			_create2DTex();
+			break;
+		case TEX_TYPE_3D:
+			_create3DTex();
+			break;
+		default:
+			freeInternalResources();
+			CM_EXCEPT(RenderingAPIException, "Unknown texture type");
+		}
+	}
+
+	void D3D11Texture::freeInternalResourcesImpl()
+	{
+		SAFE_RELEASE(mTex);
+		SAFE_RELEASE(mShaderResourceView);
+		SAFE_RELEASE(m1DTex);
+		SAFE_RELEASE(m2DTex);
+		SAFE_RELEASE(m3DTex);
+		SAFE_RELEASE(mStagingBuffer);
+	}
+
+	void D3D11Texture::_create1DTex()
+	{
+		// We must have those defined here
+		assert(mWidth > 0 || mHeight > 0);
+
+		// Determine which D3D11 pixel format we'll use
+		HRESULT hr;
+		DXGI_FORMAT d3dPF = D3D11Mappings::_getPF(D3D11Mappings::_getClosestSupportedPF(mFormat));
+
+		// Determine total number of mipmaps including main one (d3d11 convention)
+		UINT32 numMips = (mNumMipmaps == MIP_UNLIMITED || (1U << mNumMipmaps) > mWidth) ? 0 : mNumMipmaps + 1;
+
+		D3D11_TEXTURE1D_DESC desc;
+		desc.Width			= static_cast<UINT32>(mWidth);
+		desc.MipLevels		= numMips;
+		desc.ArraySize		= 1;
+		desc.Format			= d3dPF;
+		desc.Usage			= D3D11Mappings::_getUsage(mUsage);
+		desc.BindFlags		= D3D11_BIND_SHADER_RESOURCE;
+		desc.CPUAccessFlags = D3D11Mappings::_getAccessFlags(mUsage);
+		desc.MiscFlags		= 0;
+
+		// Create the texture
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		hr = device.getD3D11Device()->CreateTexture1D(&desc, nullptr, &m1DTex);
+
+		// Check result and except if failed
+		if (FAILED(hr) || device.hasError())
+		{
+			freeInternalResources();
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "Error creating texture\nError Description:" + errorDescription);
+		}
+
+		HRESULT hr = m1DTex->QueryInterface(__uuidof(ID3D11Resource), (void **)mTex);
+
+		if(FAILED(hr) || device.hasError())
+		{
+			freeInternalResources();
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "Can't get base texture\nError Description:" + errorDescription);
+		}
+
+		// Create texture view
+		D3D11_TEXTURE1D_DESC desc;
+
+		m1DTex->GetDesc(&desc);
+		mNumMipmaps = desc.MipLevels - 1;
+
+		ZeroMemory( &mSRVDesc, sizeof(mSRVDesc) );
+		mSRVDesc.Format = desc.Format;
+		mSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1D;
+		mSRVDesc.Texture1D.MipLevels = desc.MipLevels;
+		hr = device.getD3D11Device()->CreateShaderResourceView(m1DTex, &mSRVDesc, &mShaderResourceView);
+
+		if (FAILED(hr) || device.hasError())
+		{
+			String errorDescription = device.getErrorDescription(hr);
+			CM_EXCEPT(RenderingAPIException, "D3D11 device can't create shader resource view.\nError Description:" + errorDescription);
+		}
+	}
+
+	void D3D11Texture::_create2DTex()
+	{
+		// We must have those defined here
+		assert(mWidth > 0 || mHeight > 0);
+
+		// Determine which D3D11 pixel format we'll use
+		HRESULT hr;
+		DXGI_FORMAT d3dPF = D3D11Mappings::_getPF(D3D11Mappings::_getClosestSupportedPF(mFormat));
+
+		// Determine total number of mipmaps including main one (d3d11 convention)
+		UINT32 numMips = (mNumMipmaps == MIP_UNLIMITED || (1U << mNumMipmaps) > mWidth) ? 0 : mNumMipmaps + 1;
+
+		DXGI_SAMPLE_DESC sampleDesc;
+		sampleDesc.Count = 1;
+		sampleDesc.Quality = 0;
+
+		D3D11_TEXTURE2D_DESC desc;
+		desc.Width			= static_cast<UINT32>(mWidth);
+		desc.Height			= static_cast<UINT32>(mHeight);
+		desc.MipLevels		= numMips;
+		desc.ArraySize		= 1;
+		desc.Format			= d3dPF;
+		desc.SampleDesc		= sampleDesc;
+		desc.Usage			= D3D11Mappings::_getUsage(mUsage);
+		desc.BindFlags		= D3D11_BIND_SHADER_RESOURCE;
+		desc.CPUAccessFlags = D3D11Mappings::_getAccessFlags(mUsage);
+		desc.MiscFlags		= 0;
+
+        if (this->getTextureType() == TEX_TYPE_CUBE_MAP)
+        {
+                desc.MiscFlags          |= D3D11_RESOURCE_MISC_TEXTURECUBE;
+                desc.ArraySize          = 6;
+        }
+
+		// Create the texture
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		hr = device.getD3D11Device()->CreateTexture2D(&desc, nullptr, &m2DTex);
+
+		// Check result and except if failed
+		if (FAILED(hr) || device.hasError())
+		{
+			freeInternalResources();
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "Error creating texture\nError Description:" + errorDescription);
+		}
+
+		HRESULT hr = m2DTex->QueryInterface(__uuidof(ID3D11Resource), (void **)mTex);
+
+		if(FAILED(hr) || device.hasError())
+		{
+			freeInternalResources();
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "Can't get base texture\nError Description:" + errorDescription);
+		}
+
+		// Create texture view
+		D3D11_TEXTURE2D_DESC desc;
+
+		m2DTex->GetDesc(&desc);
+		mNumMipmaps = desc.MipLevels - 1;
+
+		ZeroMemory(&mSRVDesc, sizeof(mSRVDesc));
+		mSRVDesc.Format = desc.Format;
+
+		switch(getTextureType())
+		{
+		case TEX_TYPE_CUBE_MAP:
+			mSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE;
+			mSRVDesc.TextureCube.MipLevels = desc.MipLevels;
+			mSRVDesc.TextureCube.MostDetailedMip = 0;
+			break;
+
+		case TEX_TYPE_2D:
+			mSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
+			mSRVDesc.Texture2D.MostDetailedMip = 0;
+			mSRVDesc.Texture2D.MipLevels = desc.MipLevels;
+			break;
+		}
+
+		hr = device.getD3D11Device()->CreateShaderResourceView(m2DTex, &mSRVDesc, &mShaderResourceView);
+
+		if (FAILED(hr) || device.hasError())
+		{
+			String errorDescription = device.getErrorDescription(hr);
+			CM_EXCEPT(RenderingAPIException, "D3D11 device can't create shader resource view.\nError Description:" + errorDescription);
+		}
+	}
+
+	void D3D11Texture::_create3DTex()
+	{
+		// We must have those defined here
+		assert(mWidth > 0 && mHeight > 0 && mDepth > 0);
+
+		// Determine which D3D11 pixel format we'll use
+		HRESULT hr;
+		DXGI_FORMAT d3dPF = D3D11Mappings::_getPF(D3D11Mappings::_getClosestSupportedPF(mFormat));
+
+		// Determine total number of mipmaps including main one (d3d11 convention)
+		UINT numMips = (mNumMipmaps == MIP_UNLIMITED || (1U << mNumMipmaps) > std::max(std::max(mWidth, mHeight), mDepth)) ? 0 : mNumMipmaps + 1;
+
+		D3D11_TEXTURE3D_DESC desc;
+		desc.Width			= static_cast<UINT32>(mWidth);
+		desc.Height			= static_cast<UINT32>(mHeight);
+		desc.Depth			= static_cast<UINT32>(mDepth);
+		desc.MipLevels		= numMips;
+		desc.Format			= d3dPF;
+		desc.Usage			= D3D11Mappings::_getUsage(mUsage);
+		desc.BindFlags		= D3D11_BIND_SHADER_RESOURCE;
+		desc.CPUAccessFlags = D3D11Mappings::_getAccessFlags(mUsage);
+		desc.MiscFlags		= 0;
+
+		// Create the texture
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		hr = device.getD3D11Device()->CreateTexture3D(&desc, nullptr, &m3DTex);
+
+		// Check result and except if failed
+		if (FAILED(hr) || device.hasError())
+		{
+			freeInternalResources();
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "Error creating texture\nError Description:" + errorDescription);
+		}
+
+		HRESULT hr = m3DTex->QueryInterface(__uuidof(ID3D11Resource), (void **)mTex);
+
+		if(FAILED(hr) || device.hasError())
+		{
+			freeInternalResources();
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "Can't get base texture\nError Description:" + errorDescription);
+		}
+
+		// Create texture view
+		D3D11_TEXTURE3D_DESC desc;
+
+		m3DTex->GetDesc(&desc);
+		mNumMipmaps = desc.MipLevels - 1;
+
+		ZeroMemory(&mSRVDesc, sizeof(mSRVDesc));
+		mSRVDesc.Format = desc.Format;
+		mSRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D;
+		mSRVDesc.Texture3D.MostDetailedMip = 0;
+		mSRVDesc.Texture3D.MipLevels = desc.MipLevels;
+
+		hr = device.getD3D11Device()->CreateShaderResourceView(m2DTex, &mSRVDesc, &mShaderResourceView);
+
+		if (FAILED(hr) || device.hasError())
+		{
+			String errorDescription = device.getErrorDescription(hr);
+			CM_EXCEPT(RenderingAPIException, "D3D11 device can't create shader resource view.\nError Description:" + errorDescription);
+		}
+	}
+
+	void* D3D11Texture::_map(ID3D11Resource* res, D3D11_MAP flags, UINT32 mipLevel, UINT32 face)
+	{
+		D3D11_MAPPED_SUBRESOURCE pMappedResource;
+		pMappedResource.pData = nullptr;
+
+		mipLevel = Math::Clamp(mipLevel, (UINT32)mipLevel, getNumMipmaps());
+		face = Math::Clamp(face, (UINT32)0, mDepth - 1);
+
+		if(getTextureType() == TEX_TYPE_3D)
+			face = 0;
+
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+
+		mLockedSubresourceIdx = D3D11CalcSubresource(mipLevel, face, getNumMipmaps()+1);
+		device.getImmediateContext()->Map(res, mLockedSubresourceIdx, flags, 0, &pMappedResource);
+
+		if (device.hasError())
+		{
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map texture\nError Description:" + errorDescription);
+		}
+
+		return pMappedResource.pData;
+	}
+
+	void D3D11Texture::_unmap(ID3D11Resource* res)
+	{
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		device.getImmediateContext()->Unmap(res, mLockedSubresourceIdx);
+
+		if (device.hasError())
+		{
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "D3D11 device unmap resource\nError Description:" + errorDescription);
+		}
+	}
+
+	void* D3D11Texture::_mapstagingbuffer(D3D11_MAP flags, UINT32 mipLevel, UINT32 face)
+	{
+		if(!mStagingBuffer)
+			_createStagingBuffer();
+
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		device.getImmediateContext()->CopyResource(mStagingBuffer, mTex);
+
+		return _map(mStagingBuffer, flags, face, mipLevel);
+	}
+
+	void D3D11Texture::_unmapstagingbuffer()
+	{
+		_unmap(mStagingBuffer);
+	}
+
+	void* D3D11Texture::_mapstaticbuffer(PixelData lock, UINT32 mipLevel, UINT32 face)
+	{
+		UINT32 sizeOfImage = lock.getConsecutiveSize();
+		mLockedSubresourceIdx = D3D11CalcSubresource(mipLevel, face, getNumMipmaps()+1);
+
+		UINT8* bufferData = new UINT8[sizeOfImage];
+		mStaticBuffer = new PixelData(lock.getWidth(), lock.getHeight(), lock.getDepth(), lock.getFormat(), bufferData, true);
+
+		return bufferData;
+	}
+
+	void D3D11Texture::_unmapstaticbuffer()
+	{
+		size_t rowWidth = D3D11Mappings::_getSizeInBytes(mStaticBuffer->getFormat(), mStaticBuffer->getWidth());
+		size_t sliceWidth = D3D11Mappings::_getSizeInBytes(mStaticBuffer->getFormat(), mStaticBuffer->getWidth(), mStaticBuffer->getHeight());
+
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		device.getImmediateContext()->UpdateSubresource(mTex, mLockedSubresourceIdx, nullptr, mStaticBuffer->data, rowWidth, sliceWidth);
+
+		if (device.hasError())
+		{
+			String errorDescription = device.getErrorDescription();
+			CM_EXCEPT(RenderingAPIException, "D3D11 device cannot map texture\nError Description:" + errorDescription);
+		}
+
+		SAFE_DELETE(mStaticBuffer);
+	}
+
+	void D3D11Texture::_createStagingBuffer()
+	{
+		D3D11Device& device = D3D11RenderSystem::getPrimaryDevice();
+		switch (getTextureType())
+		{
+		case TEX_TYPE_1D:
+			{
+				D3D11_TEXTURE1D_DESC desc;
+				m1DTex->GetDesc(&desc);
+
+				desc.BindFlags = 0;
+				desc.MiscFlags = 0;
+				desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE | D3D11_CPU_ACCESS_READ;
+				desc.Usage = D3D11_USAGE_STAGING;
+
+				device.getD3D11Device()->CreateTexture1D(&desc, NULL, (ID3D11Texture1D**)(&mStagingBuffer));
+			} 					
+			break;
+		case TEX_TYPE_2D:
+		case TEX_TYPE_CUBE_MAP:
+		case TEX_TYPE_2D_ARRAY:
+			{
+				D3D11_TEXTURE2D_DESC desc;
+				m2DTex->GetDesc(&desc);
+
+				desc.BindFlags = 0;
+				desc.MiscFlags = 0;
+				desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE | D3D11_CPU_ACCESS_READ;
+				desc.Usage = D3D11_USAGE_STAGING;
+
+				device.getD3D11Device()->CreateTexture2D(&desc, NULL, (ID3D11Texture2D**)(&mStagingBuffer));
+			}
+			break;
+		case TEX_TYPE_3D:
+			{
+				D3D11_TEXTURE3D_DESC desc;
+				m3DTex->GetDesc(&desc);
+
+				desc.BindFlags = 0;
+				desc.MiscFlags = 0;
+				desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE | D3D11_CPU_ACCESS_READ;
+				desc.Usage = D3D11_USAGE_STAGING;
+
+				device.getD3D11Device()->CreateTexture3D(&desc, NULL, (ID3D11Texture3D**)(&mStagingBuffer));
+			}
+			break;
+		}
+	}
+}
+
+#undef THROW_IF_NOT_RENDER_THREAD

+ 52 - 53
CamelotD3D9Renderer/Include/CmD3D9HardwarePixelBuffer.h

@@ -36,8 +36,59 @@ namespace CamelotEngine {
 	class D3D9Texture;
 	class D3D9RenderTexture;
 
-	class CM_D3D9_EXPORT D3D9HardwarePixelBuffer: public HardwarePixelBuffer
+	class CM_D3D9_EXPORT D3D9HardwarePixelBuffer : public HardwarePixelBuffer
 	{
+	public:
+		D3D9HardwarePixelBuffer(HardwareBuffer::Usage usage, 
+			D3D9Texture* ownerTexture);
+		~D3D9HardwarePixelBuffer();
+
+		/// Call this to associate a D3D surface or volume with this pixel buffer
+		void bind(IDirect3DDevice9 *dev, IDirect3DSurface9 *mSurface, IDirect3DSurface9* fsaaSurface,
+			bool writeGamma, UINT32 fsaa, const String& srcName, IDirect3DBaseTexture9 *mipTex);
+		void bind(IDirect3DDevice9 *dev, IDirect3DVolume9 *mVolume, IDirect3DBaseTexture9 *mipTex);
+
+		/// @copydoc HardwarePixelBuffer::blit
+		void blit(const HardwarePixelBufferPtr &src, const Box &srcBox, const Box &dstBox);
+
+		/// @copydoc HardwarePixelBuffer::blitFromMemory
+		void blitFromMemory(const PixelData &src, const Box &dstBox);
+
+		/// @copydoc HardwarePixelBuffer::blitToMemory
+		void blitToMemory(const Box &srcBox, const PixelData &dst);
+
+		/// Internal function to update mipmaps on update of level 0
+		void _genMipmaps(IDirect3DBaseTexture9* mipTex);
+
+		/// Function to set mipmap generation
+		void _setMipmapping(bool doMipmapGen, bool HWMipmaps);
+
+
+		/// Get rendertarget for z slice
+		RenderTexture *getRenderTarget(UINT32 zoffset);
+
+		/// Accessor for surface
+		IDirect3DSurface9 *getSurface(IDirect3DDevice9* d3d9Device);
+
+		/// Accessor for AA surface
+		IDirect3DSurface9 *getFSAASurface(IDirect3DDevice9* d3d9Device);
+
+		/// Notify TextureBuffer of destruction of render target
+		virtual void _clearSliceRTT(UINT32 zoffset);
+
+		/// Release surfaces held by this pixel buffer.
+		void releaseSurfaces(IDirect3DDevice9* d3d9Device);
+
+		/// Destroy resources associated with the given device.
+		void destroyBufferResources(IDirect3DDevice9* d3d9Device);
+
+		// Called when device state is changing. Access to any device should be locked.
+		// Relevant for multi thread application.
+		static void lockDeviceAccess();
+
+		// Called when device state change completed. Access to any device is allowed.
+		// Relevant for multi thread application.
+		static void unlockDeviceAccess();
 	protected:		
 		struct BufferResources
 		{			
@@ -100,58 +151,6 @@ namespace CamelotEngine {
 		void blitFromMemory(const PixelData &src, const Box &dstBox, BufferResources* dstBufferResources);
 
 		void blitToMemory(const Box &srcBox, const PixelData &dst, BufferResources* srcBufferResources, IDirect3DDevice9* d3d9Device);
-			
-	public:
-		D3D9HardwarePixelBuffer(HardwareBuffer::Usage usage, 
-			D3D9Texture* ownerTexture);
-		~D3D9HardwarePixelBuffer();
-
-		/// Call this to associate a D3D surface or volume with this pixel buffer
-		void bind(IDirect3DDevice9 *dev, IDirect3DSurface9 *mSurface, IDirect3DSurface9* fsaaSurface,
-				  bool writeGamma, UINT32 fsaa, const String& srcName, IDirect3DBaseTexture9 *mipTex);
-		void bind(IDirect3DDevice9 *dev, IDirect3DVolume9 *mVolume, IDirect3DBaseTexture9 *mipTex);
-		
-		/// @copydoc HardwarePixelBuffer::blit
-        void blit(const HardwarePixelBufferPtr &src, const Box &srcBox, const Box &dstBox);
-		
-		/// @copydoc HardwarePixelBuffer::blitFromMemory
-		void blitFromMemory(const PixelData &src, const Box &dstBox);
-	
-		/// @copydoc HardwarePixelBuffer::blitToMemory
-		void blitToMemory(const Box &srcBox, const PixelData &dst);
-		
-		/// Internal function to update mipmaps on update of level 0
-		void _genMipmaps(IDirect3DBaseTexture9* mipTex);
-		
-		/// Function to set mipmap generation
-		void _setMipmapping(bool doMipmapGen, bool HWMipmaps);
-		
-		
-		/// Get rendertarget for z slice
-		RenderTexture *getRenderTarget(UINT32 zoffset);
-
-		/// Accessor for surface
-		IDirect3DSurface9 *getSurface(IDirect3DDevice9* d3d9Device);
-		
-		/// Accessor for AA surface
-		IDirect3DSurface9 *getFSAASurface(IDirect3DDevice9* d3d9Device);
-
-		/// Notify TextureBuffer of destruction of render target
-        virtual void _clearSliceRTT(UINT32 zoffset);
-
-		/// Release surfaces held by this pixel buffer.
-		void releaseSurfaces(IDirect3DDevice9* d3d9Device);
-
-		/// Destroy resources associated with the given device.
-		void destroyBufferResources(IDirect3DDevice9* d3d9Device);
-
-		// Called when device state is changing. Access to any device should be locked.
-		// Relevant for multi thread application.
-		static void lockDeviceAccess();
-
-		// Called when device state change completed. Access to any device is allowed.
-		// Relevant for multi thread application.
-		static void unlockDeviceAccess();
 	};
 };
 #endif

+ 3 - 3
CamelotD3D9Renderer/Source/CmD3D9HardwareIndexBuffer.cpp

@@ -119,7 +119,7 @@ namespace CamelotEngine {
 						bufferResources->mLockLength = length;
 				}
 			
-				if (bufferResources->mLockOptions != HBL_DISCARD)
+				if (bufferResources->mLockOptions != HBL_WRITE_ONLY_DISCARD)
 					bufferResources->mLockOptions = options;
 
 				++it;
@@ -246,7 +246,7 @@ namespace CamelotEngine {
 		bufferResources->mOutOfDate = true;
 		bufferResources->mLockOffset = 0;
 		bufferResources->mLockLength = getSizeInBytes();
-		bufferResources->mLockOptions = HBL_NORMAL;
+		bufferResources->mLockOptions = HBL_READ_WRITE;
 		// TODO PORT - I don't know current frame number. Once I add a method for counting frames call it here
 		//bufferResources->mLastUsedFrame = Root::getSingleton().getNextFrameNumber();
 		bufferResources->mLastUsedFrame = 0;
@@ -337,7 +337,7 @@ namespace CamelotEngine {
 		bufferResources->mOutOfDate = false;
 		bufferResources->mLockOffset = mSizeInBytes;
 		bufferResources->mLockLength = 0;
-		bufferResources->mLockOptions = HBL_NORMAL;
+		bufferResources->mLockOptions = HBL_READ_WRITE;
 
 		return true;			
 	}

+ 1 - 1
CamelotD3D9Renderer/Source/CmD3D9HardwarePixelBuffer.cpp

@@ -336,7 +336,7 @@ PixelData D3D9HardwarePixelBuffer::lockImpl(const Box lockBox,  LockOptions opti
 	DWORD flags = 0;
 	switch(options)
 	{
-	case HBL_DISCARD:
+	case HBL_WRITE_ONLY_DISCARD:
 		// D3D only likes D3DLOCK_DISCARD if you created the texture with D3DUSAGE_DYNAMIC
 		// debug runtime flags this up, could cause problems on some drivers
 		if (mUsage & HBU_DYNAMIC)

+ 3 - 3
CamelotD3D9Renderer/Source/CmD3D9HardwareVertexBuffer.cpp

@@ -119,7 +119,7 @@ namespace CamelotEngine {
 						bufferResources->mLockLength = length;
 				}
 				
-				if (bufferResources->mLockOptions != HBL_DISCARD)
+				if (bufferResources->mLockOptions != HBL_WRITE_ONLY_DISCARD)
 					bufferResources->mLockOptions = options;					
 
 				++it;
@@ -245,7 +245,7 @@ namespace CamelotEngine {
 		bufferResources->mOutOfDate = true;
 		bufferResources->mLockOffset = 0;
 		bufferResources->mLockLength = getSizeInBytes();
-		bufferResources->mLockOptions = HBL_NORMAL;
+		bufferResources->mLockOptions = HBL_READ_WRITE;
 
 		// TODO PORT - Don't know what the next frame number is. Add a method for that
 		//bufferResources->mLastUsedFrame = Root::getSingleton().getNextFrameNumber();
@@ -336,7 +336,7 @@ namespace CamelotEngine {
 		bufferResources->mOutOfDate = false;
 		bufferResources->mLockOffset = mSizeInBytes;
 		bufferResources->mLockLength = 0;
-		bufferResources->mLockOptions = HBL_NORMAL;
+		bufferResources->mLockOptions = HBL_READ_WRITE;
 
 		return true;		
 	}

+ 14 - 0
CamelotGLRenderer/Include/CmGLDepthStencilBuffer.h

@@ -0,0 +1,14 @@
+#pragma once
+
+#include "CmGLPrerequisites.h"
+#include "CmDepthStencilBuffer.h"
+
+namespace CamelotEngine
+{
+	class CM_RSGL_EXPORT GLDepthStencilBuffer : public DepthStencilBuffer
+	{
+	public:
+		GLDepthStencilBuffer(UINT32 bitDepth, UINT32 width, UINT32 height, UINT32 fsaa, const String &fsaaHint);
+		// TODO - Add GL specific implementation
+	};
+}

+ 2 - 2
CamelotGLRenderer/Source/CmGLHardwareIndexBuffer.cpp

@@ -86,7 +86,7 @@ namespace CamelotEngine {
 				mScratchPtr = retPtr;
 				mScratchUploadOnUnlock = (options != HBL_READ_ONLY);
 
-				if (options != HBL_DISCARD)
+				if (options != HBL_WRITE_ONLY_DISCARD)
 				{
 					// have to read back the data before returning the pointer
 					readData(offset, length, retPtr);
@@ -98,7 +98,7 @@ namespace CamelotEngine {
 		{
 			glBindBufferARB( GL_ELEMENT_ARRAY_BUFFER_ARB, mBufferId );
 			// Use glMapBuffer
-			if(options == HBL_DISCARD)
+			if(options == HBL_WRITE_ONLY_DISCARD)
 			{
 				// Discard the buffer
 				glBufferDataARB(GL_ELEMENT_ARRAY_BUFFER_ARB, mSizeInBytes, NULL, 

+ 2 - 2
CamelotGLRenderer/Source/CmGLHardwareVertexBuffer.cpp

@@ -88,7 +88,7 @@ namespace CamelotEngine {
 				mScratchPtr = retPtr;
 				mScratchUploadOnUnlock = (options != HBL_READ_ONLY);
 
-				if (options != HBL_DISCARD)
+				if (options != HBL_WRITE_ONLY_DISCARD)
 				{
 					// have to read back the data before returning the pointer
 					readData(offset, length, retPtr);
@@ -101,7 +101,7 @@ namespace CamelotEngine {
 			// Use glMapBuffer
 			glBindBufferARB( GL_ARRAY_BUFFER_ARB, mBufferId );
 			// Use glMapBuffer
-			if(options == HBL_DISCARD)
+			if(options == HBL_WRITE_ONLY_DISCARD)
 			{
 				// Discard the buffer
 				glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL, 

+ 21 - 0
CamelotRenderer/Include/CmCommon.h

@@ -203,6 +203,27 @@ namespace CamelotEngine {
 		SOP_INVERT
 	};
 
+	/// Locking options
+	enum LockOptions
+	{
+        /** Normal mode, ie allows read/write and contents are preserved. */
+        HBL_READ_WRITE,
+		/** Discards the <em>entire</em> buffer while locking; this allows optimisation to be 
+		performed because synchronisation issues are relaxed. 
+		*/
+		HBL_WRITE_ONLY_DISCARD,
+		/** Lock the buffer for reading only. Not allowed in buffers which are created with HBU_WRITE_ONLY. 
+		*/ 
+		HBL_READ_ONLY,
+        /** As HBL_NORMAL, except the application guarantees not to overwrite any 
+        region of the buffer which has already been used in this frame, can allow
+        some optimisation on some APIs. */
+        HBL_WRITE_ONLY_NO_OVERWRITE,
+		/** Lock for writing only */
+		HBL_WRITE_ONLY
+    			
+	};
+
 	/** Texture addressing mode for each texture coordinate. */
 	struct UVWAddressingMode
 	{

+ 1 - 18
CamelotRenderer/Include/CmHardwareBuffer.h

@@ -30,6 +30,7 @@ THE SOFTWARE.
 
 // Precompiler options
 #include "CmPrerequisites.h"
+#include "CmCommon.h"
 
 namespace CamelotEngine {
 
@@ -115,24 +116,6 @@ namespace CamelotEngine {
                 HBU_DYNAMIC_WRITE_ONLY_DISCARDABLE = 14
 
 
-		    };
-		    /// Locking options
-		    enum LockOptions
-		    {
-                /** Normal mode, ie allows read/write and contents are preserved. */
-                HBL_NORMAL,
-			    /** Discards the <em>entire</em> buffer while locking; this allows optimisation to be 
-				performed because synchronisation issues are relaxed. 
-			    */
-			    HBL_DISCARD,
-			    /** Lock the buffer for reading only. Not allowed in buffers which are created with HBU_WRITE_ONLY. 
-				*/ 
-			    HBL_READ_ONLY,
-                /** As HBL_NORMAL, except the application guarantees not to overwrite any 
-                region of the buffer which has already been used in this frame, can allow
-                some optimisation on some APIs. */
-                HBL_NO_OVERWRITE
-    			
 		    };
 	    protected:
 		    UINT32 mSizeInBytes;

+ 0 - 1
CamelotRenderer/Include/CmHardwarePixelBuffer.h

@@ -60,7 +60,6 @@ namespace CamelotEngine {
         PixelData mCurrentLock;
 		// The current locked box of this surface (entire surface coords)
 		Box mLockedBox;
-
         
         /// Internal implementation of lock(), must be overridden in subclasses
         virtual PixelData lockImpl(const Box lockBox,  LockOptions options) = 0;

+ 7 - 17
CamelotRenderer/Include/CmTexture.h

@@ -46,18 +46,10 @@ namespace CamelotEngine {
     enum TextureUsage
     {
 		/// @copydoc HardwareBuffer::Usage
-		TU_STATIC = HardwareBuffer::HBU_STATIC,
-		TU_DYNAMIC = HardwareBuffer::HBU_DYNAMIC,
-		TU_WRITE_ONLY = HardwareBuffer::HBU_WRITE_ONLY,
-		TU_STATIC_WRITE_ONLY = HardwareBuffer::HBU_STATIC_WRITE_ONLY, 
-		TU_DYNAMIC_WRITE_ONLY = HardwareBuffer::HBU_DYNAMIC_WRITE_ONLY,
-		TU_DYNAMIC_WRITE_ONLY_DISCARDABLE = HardwareBuffer::HBU_DYNAMIC_WRITE_ONLY_DISCARDABLE,
-		/// this texture will be a render target, i.e. used as a target for render to texture
-		/// setting this flag will ignore all other texture usages
-		TU_RENDERTARGET = 0x200,
-		/// default to automatic mipmap generation static textures
-		TU_DEFAULT = TU_STATIC_WRITE_ONLY
-        
+		TU_STATIC = HardwareBuffer::HBU_STATIC, // Optimal setting if texture is read by the GPU often, and very rarely written by CPU
+		TU_DYNAMIC = HardwareBuffer::HBU_DYNAMIC, // Optimal if the texture is updated by CPU often (e.g. every frame)
+		TU_RENDERTARGET = 0x200, // Used for rendering by the GPU
+		TU_DEFAULT = TU_STATIC
     };
 
     /** Enum identifying the texture type
@@ -191,7 +183,7 @@ namespace CamelotEngine {
 		 *
 		 * @see		Texture::setRawPixels
 		 */
-		void setRawPixels_internal(const PixelData& data, UINT32 face = 0, UINT32 mip = 0);
+		virtual void setRawPixels_internal(const PixelData& data, UINT32 face = 0, UINT32 mip = 0);
 
 		/**
 		 * @brief	Gets raw pixels from the texture. This is a slow operation
@@ -219,11 +211,11 @@ namespace CamelotEngine {
 		 *
 		 * @see		Texture::getRawPixels
 		 */
-		void getRawPixels_internal(UINT32 face, UINT32 mip, AsyncOp& op);
+		virtual void getRawPixels_internal(UINT32 face, UINT32 mip, AsyncOp& op);
 
 		/** Copies (and maybe scales to fit) the contents of this texture to
 			another texture. */
-		virtual void copy_internal( TexturePtr& target );
+		virtual void copy_internal(TexturePtr& target);
 
     protected:
 		friend class TextureManager;
@@ -310,9 +302,7 @@ namespace CamelotEngine {
 			PixelFormat format, int usage = TU_DEFAULT,
 			bool hwGammaCorrection = false, UINT32 fsaa = 0, const String& fsaaHint = StringUtil::BLANK);
     };
-
 	/** @} */
-
 }
 
 #endif

+ 2 - 2
CamelotRenderer/Source/CmHardwarePixelBuffer.cpp

@@ -102,12 +102,12 @@ namespace CamelotEngine
 		}
 		const PixelData &srclock = src->lock(srcBox, HBL_READ_ONLY);
 
-		LockOptions method = HBL_NORMAL;
+		LockOptions method = HBL_READ_WRITE;
 		if(dstBox.left == 0 && dstBox.top == 0 && dstBox.front == 0 &&
 		   dstBox.right == mWidth && dstBox.bottom == mHeight &&
 		   dstBox.back == mDepth)
 			// Entire buffer -- we can discard the previous contents
-			method = HBL_DISCARD;
+			method = HBL_WRITE_ONLY_DISCARD;
 			
 		const PixelData &dstlock = lock(dstBox, method);
 		if(dstlock.getWidth() != srclock.getWidth() ||

+ 1 - 1
CamelotRenderer/Source/CmTexture.cpp

@@ -123,7 +123,7 @@ namespace CamelotEngine {
 		if(mip < 0 || mip > mNumMipmaps)
 			CM_EXCEPT(InvalidParametersException, "Invalid mip level: " + toString(mip) + ". Min is 0, max is " + toString(mNumMipmaps));
 
-		if(face < 0 || mip > getNumFaces())
+		if(face < 0 || face > getNumFaces())
 			CM_EXCEPT(InvalidParametersException, "Invalid face index: " + toString(face) + ". Min is 0, max is " + toString(getNumFaces()));
 
 		if(mFormat != data.format)

+ 13 - 1
CamelotRenderer/TODO.txt

@@ -17,14 +17,25 @@
 
 
 /////
+HardwarePixelBuffer should hold a pointer to DX11Texture, and CmDX11Texture should hold a pointer to HardwarePixelBuffer
+
 waitForVsync can probably be moved somewhere other than being directly in RenderSystem? (where is it in DX11?)
 
 Move createRenderTexture to TextureManager? (also createMultiRenderTexture)
- - Right now its created with a special texture usage flag, which I don't like
+ - Right now its created with a special texture usage flag, which I don't like (Textures have slices and other weird stuff)
 Drop OpenGL support for low level shaders? (See if cg can translate to GLSL)
 
 Keeping a list of all render targets in RenderSystem shouldn't be needed (and calling attach/detach renderTarget). Renderer should determine in what order are render targets presented.
 
+Constant buffers are created in a weird way. Maybe they should only be created internally by GpuProgramParameters?
+ - Multiple GpuProgramParameters get returned from GpuProgram after createParameters() is called, in a map, each with its own name
+
+
+setDepthBuffer method on RenderTexture
+All render targets need to create DepthStencilBuffer internally, so that getDepthStencilBuffer can return something. Right now only D3D11 render window does this
+Add D3D11DepthStencilBuffer
+ - Remove commented out buffer creation code from D3D11RenderWindow
+
 Make CommandQueue not use mutexes and use atomics instead??
 Make sure that the simulation can't run faster then the render thread! (Block the main thread until previous render finishes)
 /////
@@ -169,6 +180,7 @@ Optional TODO:
 After everything is polished
  - Each view (i.e. camera) of the scene should be put into its own thread
  - How do I handle multiple mesh formats? Some files need animation, other don't. Some would mabye like to use QTangent, others the proper tangent frame.
+  - Asset postprocessor? Imports a regular mesh using normal importers and then postprocesses it into a specialized format?
  - Load texture mips separately so we can unload HQ textures from far away objects (like UE3)
  - Add Unified shader so I can easily switch between HLSL and GLSL shaders (they need same parameters usually, just different code)
     - Maybe just add support for Cg and force everyone to use that? - I'd like to be able to just switch out renderer in a single location and that everything keeps on working without 

+ 2 - 0
CamelotUtility/Include/CmPixelData.h

@@ -241,6 +241,8 @@ namespace CamelotEngine
         */
         UINT32 getSliceSkip() const { return slicePitch - (getHeight() * rowPitch); }
 
+		PixelFormat getFormat() const { return format; }
+
         /** Return whether this buffer is laid out consecutive in memory (ie the pitches
          	are equal to the dimensions)
         */