Переглянути джерело

Fixes to DX9 device reset

Marko Pintera 11 роки тому
батько
коміт
f4606177a5

+ 8 - 12
CamelotD3D9Renderer/Include/CmD3D9RenderSystem.h

@@ -157,23 +157,19 @@ namespace BansheeEngine
 		void registerWindow(RenderWindow& renderWindow);
 		void registerWindow(RenderWindow& renderWindow);
 
 
 	private:
 	private:
-		/// Direct3D
-		IDirect3D9*	 mpD3D;		
+		static D3D9RenderSystem* msD3D9RenderSystem;
+
+		IDirect3D9*	mpD3D;
+		bool mIsFrameInProgress;
+		bool mRestoreFrameOnReset;
+
+		mutable D3D9DriverList* mDriverList;
+		D3D9Driver* mActiveD3DDriver;
 
 
-		/// instance
 		HINSTANCE mhInstance;
 		HINSTANCE mhInstance;
 
 
 		UINT32 mViewportLeft, mViewportTop, mViewportWidth, mViewportHeight;
 		UINT32 mViewportLeft, mViewportTop, mViewportWidth, mViewportHeight;
-		// Scissor test rectangle
 		RECT mScissorRect;
 		RECT mScissorRect;
-		/// List of D3D drivers installed (video cards)
-		mutable D3D9DriverList* mDriverList; // TODO - Mutable because it gets constructed in getDirect3DDrivers(). Change that.
-		/// Currently active driver
-		D3D9Driver* mActiveD3DDriver;
-		/// NVPerfHUD allowed?
-		bool mUseNVPerfHUD;
-		/// Fast singleton access.
-		static D3D9RenderSystem* msD3D9RenderSystem;
 
 
 		DrawOperationType mCurrentDrawOperation;
 		DrawOperationType mCurrentDrawOperation;
 
 

+ 18 - 8
CamelotD3D9Renderer/Source/CmD3D9RenderSystem.cpp

@@ -48,10 +48,9 @@ namespace BansheeEngine
 	D3D9RenderSystem* D3D9RenderSystem::msD3D9RenderSystem = NULL;
 	D3D9RenderSystem* D3D9RenderSystem::msD3D9RenderSystem = NULL;
 
 
 	D3D9RenderSystem::D3D9RenderSystem( HINSTANCE hInstance )
 	D3D9RenderSystem::D3D9RenderSystem( HINSTANCE hInstance )
-		: mTexStageDesc(nullptr)
-		, mNumTexStages(0)
-		, mCurrentDrawOperation(DOT_TRIANGLE_LIST)
-		, mViewportLeft(0), mViewportTop(0), mViewportWidth(0), mViewportHeight(0)
+		: mTexStageDesc(nullptr), mNumTexStages(0), mCurrentDrawOperation(DOT_TRIANGLE_LIST), 
+		mViewportLeft(0), mViewportTop(0), mViewportWidth(0), mViewportHeight(0),
+		mIsFrameInProgress(false), mRestoreFrameOnReset(false)
 	{
 	{
 		// update singleton access pointer.
 		// update singleton access pointer.
 		msD3D9RenderSystem = this;
 		msD3D9RenderSystem = this;
@@ -63,7 +62,6 @@ namespace BansheeEngine
 		mpD3D = NULL;		
 		mpD3D = NULL;		
 		mDriverList = NULL;
 		mDriverList = NULL;
 		mActiveD3DDriver = NULL;	
 		mActiveD3DDriver = NULL;	
-		mUseNVPerfHUD = false;
 		mHLSLProgramFactory = NULL;		
 		mHLSLProgramFactory = NULL;		
 		mDeviceManager = NULL;	
 		mDeviceManager = NULL;	
 		mResourceManager = nullptr;	
 		mResourceManager = nullptr;	
@@ -1153,14 +1151,14 @@ namespace BansheeEngine
 		THROW_IF_NOT_CORE_THREAD;
 		THROW_IF_NOT_CORE_THREAD;
 
 
 		HRESULT hr;
 		HRESULT hr;
-
-		if( FAILED( hr = getActiveD3D9Device()->BeginScene() ) )
+		if(FAILED(hr = getActiveD3D9Device()->BeginScene()))
 		{
 		{
 			String msg = DXGetErrorDescription(hr);
 			String msg = DXGetErrorDescription(hr);
 			CM_EXCEPT(RenderingAPIException, "Error beginning frame :" + msg);
 			CM_EXCEPT(RenderingAPIException, "Error beginning frame :" + msg);
 		}
 		}
 
 
  		mDeviceManager->getActiveDevice()->clearDeviceStreams();
  		mDeviceManager->getActiveDevice()->clearDeviceStreams();
+		mIsFrameInProgress = true;
 	}
 	}
 
 
 	void D3D9RenderSystem::endFrame()
 	void D3D9RenderSystem::endFrame()
@@ -1170,6 +1168,8 @@ namespace BansheeEngine
 		HRESULT hr;
 		HRESULT hr;
 		if(FAILED(hr = getActiveD3D9Device()->EndScene()))
 		if(FAILED(hr = getActiveD3D9Device()->EndScene()))
 			CM_EXCEPT(RenderingAPIException, "Error ending frame");
 			CM_EXCEPT(RenderingAPIException, "Error ending frame");
+
+		mIsFrameInProgress = false;
 	}
 	}
 
 
 	void D3D9RenderSystem::setVertexDeclaration(VertexDeclarationPtr decl)
 	void D3D9RenderSystem::setVertexDeclaration(VertexDeclarationPtr decl)
@@ -2234,7 +2234,11 @@ namespace BansheeEngine
 
 
 	void D3D9RenderSystem::notifyOnDeviceLost(D3D9Device* device)
 	void D3D9RenderSystem::notifyOnDeviceLost(D3D9Device* device)
 	{	
 	{	
-
+		if (mIsFrameInProgress)
+		{
+			endFrame();
+			mRestoreFrameOnReset = true;
+		}
 	}
 	}
 
 
 	void D3D9RenderSystem::notifyOnDeviceReset(D3D9Device* device)
 	void D3D9RenderSystem::notifyOnDeviceReset(D3D9Device* device)
@@ -2242,6 +2246,12 @@ namespace BansheeEngine
 		// Reset state attributes.	
 		// Reset state attributes.	
 		mVertexProgramBound = false;
 		mVertexProgramBound = false;
 		mFragmentProgramBound = false;
 		mFragmentProgramBound = false;
+
+		if (mRestoreFrameOnReset)
+		{
+			beginFrame();
+			mRestoreFrameOnReset = false;
+		}
 	}
 	}
 
 
 	void D3D9RenderSystem::determineFSAASettings(IDirect3DDevice9* d3d9Device,
 	void D3D9RenderSystem::determineFSAASettings(IDirect3DDevice9* d3d9Device,

+ 0 - 1
CamelotD3D9Renderer/Source/CmD3D9RenderWindow.cpp

@@ -585,7 +585,6 @@ namespace BansheeEngine
 			{
 			{
 				presentParams->PresentationInterval = D3DPRESENT_INTERVAL_ONE;
 				presentParams->PresentationInterval = D3DPRESENT_INTERVAL_ONE;
 			}
 			}
-
 		}
 		}
 		else
 		else
 		{
 		{

+ 6 - 3
Polish.txt

@@ -16,6 +16,7 @@ Finish GPUProfiler:
  Fullscreen stuff:
  Fullscreen stuff:
 
 
 When initializing a render window I don't have an option to use exact refresh rate (i.e. in RENDER_WINDOW_DESC)
 When initializing a render window I don't have an option to use exact refresh rate (i.e. in RENDER_WINDOW_DESC)
+ - Likely use a VideoMode you can create manually
 
 
 Add a better way of specifying FSAA (and don't call it FSAA because it's multisampling)
 Add a better way of specifying FSAA (and don't call it FSAA because it's multisampling)
  - fsaaHint is useless in most cases. Add an Enum instead.
  - fsaaHint is useless in most cases. Add an Enum instead.
@@ -26,12 +27,14 @@ I should be able to specify resolution when going to windowed mode
 OpenGL going back from windowed mode doesn't restore window style properly.
 OpenGL going back from windowed mode doesn't restore window style properly.
 OpenGL doesn't list windows in the same order as DirectX
 OpenGL doesn't list windows in the same order as DirectX
 
 
-DirectX 9 still crashes when going to fullscreen (presumably only when using retail DX9 runtime)
-Switching from higher to lower resoltuion in DX9 causes an issue where viewport is larger than the render target. 
-Test DirectX 9 full-screen on another monitor
+Switching from higher to lower resoltuion in DX9 causes an issue where viewport is larger than the render target. (Only with debug runtime - Can probably ignore)
+When toggling fullscreen two times device reset fails
 In DX9 render window I have disabled top most style.
 In DX9 render window I have disabled top most style.
   - If needed re-enable it, if not remove it from OpenGL as well as I think it disables alt+tab
   - If needed re-enable it, if not remove it from OpenGL as well as I think it disables alt+tab
 
 
+DISREGARD MONITOR INDEX ON DX9
+ - It's not trivial and its not worth wasting time on a deprecated system
+
 LATER:
 LATER:
  Add ability to change FSAA on RenderWindow.
  Add ability to change FSAA on RenderWindow.
   - Maybe later. OpenGL requires window to be re-created for it to change I think. As SetPixelFormat is allowed to be called just once per window
   - Maybe later. OpenGL requires window to be re-created for it to change I think. As SetPixelFormat is allowed to be called just once per window