Sign in to follow this  

OpenGL SwapChain DX10

This topic is 2859 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

heyhey, It's almost driving me crazy... I wrote an independent renderer (OpenGL/DX10). The problem is the aspect ratio of the DX10 renderer. When I use a single window to render everything goes fine ( So I assume my matrices/Viewport-setup) is correct. when I use 2 windows (wxWidgets and a splitter) the rendering is screwed up (but only the DX-one). As both share some code I guess the problem is somehow related to the swapchains.
bool MxD3D10Renderer::DrawWindow( MxWindow* pWindow )
{
	_MxWindowD3D10* pWindowData = GetD3D10WindowStruct( pWindow );

	// Check dx10struct for validity! An Error Here Must be traced immediately!!!
	MxAssert( pWindowData );
	MxAssert( pWindowData->m_pRenderTargetView != 0 && pWindowData->m_pSwapChain != 0 && pWindowData->m_pDepthStencilView != 0 );

	// Some SwapChain Checking:
	{
		//DXGI_SURFACE_DESC swapDesc;
		DXGI_SWAP_CHAIN_DESC swapDesc;

		pWindowData->m_pSwapChain->GetDesc( &swapDesc );
		MxAssert( swapDesc.BufferDesc.Width  == pWindow->GetWxWindow()->GetSize().GetWidth() );
		MxAssert( swapDesc.BufferDesc.Height == pWindow->GetWxWindow()->GetSize().GetHeight() );
	}

	m_pD3DDevice->OMSetRenderTargets( 1, &pWindowData->m_pRenderTargetView, pWindowData->m_pDepthStencilView );

	float ClearColor[4] = { 0.176f, 0.196f, 0.667f, 1.0f };

	m_pD3DDevice->ClearRenderTargetView( pWindowData->m_pRenderTargetView, ClearColor );

	m_pD3DDevice->ClearDepthStencilView( pWindowData->m_pDepthStencilView, D3D10_CLEAR_DEPTH|D3D10_CLEAR_STENCIL, 1.f, 0 );

	std::list< MxSceneView* >& refSceneViews = pWindow->GetConnectedViews();
	std::list< MxSceneView* >::iterator itor;


	D3D10_VIEWPORT vp;
	vp.Width = pWindow->GetWxWindow()->GetSize().GetWidth();
	vp.Height = pWindow->GetWxWindow()->GetSize().GetHeight();
	vp.MinDepth = 0.0f;
	vp.MaxDepth = 1.0f;
	vp.TopLeftX = 0;
	vp.TopLeftY = 0;
	m_pD3DDevice->RSSetViewports( 1, &vp );


	for ( itor = refSceneViews.begin(); itor != refSceneViews.end(); ++itor ) {
		// Call superclass for rendering
		Render( (*itor), &pWindow->m_WindowRenderOptions );
	}

	// todo: might be that the vsynching under dx10 is the first parameter of the present-call, might set to 1
	if ( FAILED ( pWindowData->m_pSwapChain->Present( 0, 0 ) ) ) {
		MxAssert( 0 );
		return false;
	}
}

each window has it's own swapchain and depth/stencil texture that are created like this (resizing uses almost the same)
bool MxD3D10Renderer::MakeWindowCompatible( MxWindow* pWindow )
{
	MX_FUNCTION_BEGIN();

	if ( !pWindow ) return false;
	MxWindowWin32* pWindowWin32 = static_cast< MxWindowWin32* > ( pWindow );

	// descriptions:
	wxSize wndSize = pWindowWin32->GetSize();
	int iWidth = wndSize.GetWidth();
	int iHeight = wndSize.GetHeight();

	RECT rect;
	GetClientRect( (HWND)pWindowWin32->GetHWND(), &rect );
	iWidth = rect.right - rect.left;
	iHeight = rect.bottom - rect.top;

	iWidth  = std::max( 1, iWidth );
	iHeight = std::max( 1, iHeight );

	DXGI_FORMAT format = DXGI_FORMAT_R8G8B8A8_UNORM;			// 32Bit + Alpha
	int iNumSamples = 1 << 3;
	
	// check maximum multisampling
	MxAssert( iNumSamples <= D3D10_MAX_MULTISAMPLE_SAMPLE_COUNT );
	
	// Check the format that was set above
	UINT uiFormatSupport = 0;
	if ( FAILED( m_pD3DDevice->CheckFormatSupport( format, &uiFormatSupport ) ) ) {
		MxAssert( 0 );
		return false;
	}

	// Check the multisampling and quality settings:
	UINT SampleCount = iNumSamples;								// MSDN: "The default sampler mode, with no anti-aliasing, has a count of 1 and a quality level of 0."
	UINT NumQualityLevels = 0;

	if ( FAILED( m_pD3DDevice->CheckMultisampleQualityLevels( format, SampleCount, &NumQualityLevels ) ) ) {
		MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to check multisample quality levels!\n";
		MxAssert( 0 );
		return false;
	}
	if ( NumQualityLevels == 0 ) {								// 0 means not compatible
		MX_LOG_MAIN << MX_LOG_FUNCTION << "Multisample quality levels == 0!\n";
		MxAssert( 0 );
		return false;
	}

	UINT Quality = NumQualityLevels-1;							// can range from 0 to QualityLevels-1

	DXGI_SAMPLE_DESC sampledesc;
	sampledesc.Count		= SampleCount;
	sampledesc.Quality		= Quality;

	// Fill out Swap Chain
	DXGI_SWAP_CHAIN_DESC dsc				= {0};
	dsc.BufferDesc.Width					= iWidth;
	dsc.BufferDesc.Height					= iHeight;
	dsc.BufferDesc.RefreshRate.Denominator	= 1;				// 60Hz
	dsc.BufferDesc.RefreshRate.Numerator	= 60;
	dsc.BufferDesc.Format					= format;
	dsc.BufferDesc.Scaling					= DXGI_MODE_SCALING_UNSPECIFIED;
	dsc.BufferDesc.ScanlineOrdering			= DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED;
	dsc.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;			// Use as Render Target
	dsc.BufferCount = 1;	
	dsc.OutputWindow = (HWND)pWindowWin32->GetHWND();			// hwnd of window
	dsc.Windowed = true;
	dsc.SampleDesc = sampledesc;								// Number of samples per pixel
	dsc.SwapEffect = DXGI_SWAP_EFFECT_DISCARD;					// Switch pointers instead of copying
	dsc.Flags = 0;												// No Flags

	//_MxWindowD3D10 compatibleWindow;
	_MxWindowD3D10* pWindowData = GetD3D10WindowStruct( pWindow );// new _MxWindowD3D10();

	
	// create a swap-chain for that window
	if ( FAILED ( m_pFactory->CreateSwapChain( m_pD3DDevice, &dsc, &pWindowData->m_pSwapChain ) ) ) {
		MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to create Swap Chain!\n";
		MxAssert( 0 );
		return false;
	}

	// retrieve the backbuffer ( it's a com resource )
	ID3D10Texture2D* pBackBuffer;
	if ( FAILED ( pWindowData->m_pSwapChain->GetBuffer( 0, __uuidof( ID3D10Texture2D ), reinterpret_cast< void** >( &pBackBuffer ) ) ) ) {
		MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to retrieve SwapChain Backbuffer!\n";
		MxAssert( 0 );
		return false;
	}
	// Create a RenderTargetView from the backbuffer
	if ( FAILED ( m_pD3DDevice->CreateRenderTargetView( pBackBuffer, 0, &pWindowData->m_pRenderTargetView ) ) ) {
		MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to Create RenderTargetView!\n";
		MxAssert( 0 );
		return false;
	}
	// release com-resource
	pBackBuffer->Release();
	
	// also create a depth/stencil buffer for this window:
	D3D10_TEXTURE2D_DESC depthStencilDesc;
	depthStencilDesc.Width              = iWidth;
	depthStencilDesc.Height             = iHeight;
	depthStencilDesc.MipLevels          = 1;										// Only one mipmap-level
	depthStencilDesc.ArraySize          = 1;										// Only 1 texture
	depthStencilDesc.Format             = DXGI_FORMAT_D32_FLOAT;

	depthStencilDesc.SampleDesc	= sampledesc;								// Sample description must match
	depthStencilDesc.Usage              = D3D10_USAGE_DEFAULT;						// cannot be read/written by CPU
	depthStencilDesc.BindFlags          = D3D10_BIND_DEPTH_STENCIL;
	depthStencilDesc.CPUAccessFlags     = 0;
	depthStencilDesc.MiscFlags          = 0;

	if ( FAILED ( m_pD3DDevice->CreateTexture2D( &depthStencilDesc, 0, &pWindowData->m_pDepthStencilBuffer ) ) ) {
		MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to create 2D Texture for window!\n";
		MxAssert( 0 );
		return false;
	}

	// Create the depth stencil view
	D3D10_DEPTH_STENCIL_VIEW_DESC descDSV;
	descDSV.Format = depthStencilDesc.Format;
	descDSV.ViewDimension = D3D10_DSV_DIMENSION_TEXTURE2DMS;
	descDSV.Texture2D.MipSlice = 0;

	if ( FAILED ( m_pD3DDevice->CreateDepthStencilView( pWindowData->m_pDepthStencilBuffer, &descDSV, &pWindowData->m_pDepthStencilView ) ) ) {
		MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to create depth stencil view for window!\n";
		MxAssert( 0 );
		return false;
	}

	pWindowWin32->SetUserData( pWindowData );

	return true;
}

I get no error or assert-break whatsoever. I checked the matrices and compared them with the rendering of a single window (regarding a specific size and stuff). The only thing that I found on the internet was on how to actually create different swap-chains for each window (as I do above). My device is created without a swapchain ("D3D10CreateDevice"). When I use a wxSplitter and only render one window (and the other wxPanel) everything goes fine.. I have no clue anymore where to look for the error. Please, please help me. thanks in advance zqueezy

Share this post


Link to post
Share on other sites
More code? Please I'm desperate... :)
Some is not optimized... mostly the same as the MakeCompatible


bool MxD3D10Renderer::ResizeWindow( MxWindow* pWindow, int iWidth, int iHeight )
{
if ( !pWindow ) return true;

_MxWindowD3D10* pWindowData = GetD3D10WindowStruct( pWindow );

if ( pWindowData->m_pSwapChain == 0 || pWindowData->m_pRenderTargetView == 0 ) {
/// Window is not ready yet...
return false;
}

// Get safe with and height for resizing
iHeight = std::max( 1, iHeight );
iWidth = std::max( 1, iWidth );


DXGI_SWAP_CHAIN_DESC swapDesc;
pWindowData->m_pSwapChain->GetDesc( &swapDesc );

pWindowData->m_pRenderTargetView->Release();
pWindowData->m_pDepthStencilView->Release();
pWindowData->m_pDepthStencilBuffer->Release();

pWindowData->m_pSwapChain->ResizeBuffers( swapDesc.BufferCount, (UINT)iWidth, (UINT)iHeight, DXGI_FORMAT_UNKNOWN, 0 );

// retrieve the backbuffer ( it's a com resource )
ID3D10Texture2D* pBackBuffer;
if ( FAILED ( pWindowData->m_pSwapChain->GetBuffer( 0, __uuidof( ID3D10Texture2D ), reinterpret_cast< void** >( &pBackBuffer ) ) ) ) {
MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to retrieve SwapChain Backbuffer!\n";
MxAssert( 0 );
return false;
}
// Get a rendertargetview for the backbuffer
if ( FAILED ( m_pD3DDevice->CreateRenderTargetView( pBackBuffer, 0, &pWindowData->m_pRenderTargetView ) ) ) {
MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to Create RenderTargetView!\n";
MxAssert( 0 );
return false;
}
// release com-resource
pBackBuffer->Release();

DXGI_FORMAT format = DXGI_FORMAT_R8G8B8A8_UNORM;
int iNumSamples = 1 << 3;

// check maximum multisampling
MxAssert( iNumSamples <= D3D10_MAX_MULTISAMPLE_SAMPLE_COUNT );

// Check the format that was set above
UINT uiFormatSupport = 0;
if ( FAILED( m_pD3DDevice->CheckFormatSupport( format, &uiFormatSupport ) ) ) {
MxAssert( 0 );
return false;
}

// Check the multisampling and quality settings:
UINT SampleCount = iNumSamples; // MSDN: "The default sampler mode, with no anti-aliasing, has a count of 1 and a quality level of 0."
UINT NumQualityLevels = 0;

if ( FAILED( m_pD3DDevice->CheckMultisampleQualityLevels( format, SampleCount, &NumQualityLevels ) ) ) {
MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to check multisample quality levels!\n";
MxAssert( 0 );
return false;
}
if ( NumQualityLevels == 0 ) { // 0 means not compatible
MX_LOG_MAIN << MX_LOG_FUNCTION << "Multisample quality levels == 0!\n";
MxAssert( 0 );
return false;
}

UINT Quality = NumQualityLevels-1; // can range from 0 to QualityLevels-1

DXGI_SAMPLE_DESC sampledesc;
sampledesc.Count = SampleCount;
sampledesc.Quality = Quality;


// also create a depth/stencil buffer for this window:
D3D10_TEXTURE2D_DESC depthStencilDesc;
depthStencilDesc.Width = iWidth;
depthStencilDesc.Height = iHeight;
depthStencilDesc.MipLevels = 1; // Only one mipmap-level
depthStencilDesc.ArraySize = 1; // Only 1 texture
//depthStencilDesc.Format = DXGI_FORMAT_D24_UNORM_S8_UINT;
depthStencilDesc.Format = DXGI_FORMAT_D32_FLOAT;


depthStencilDesc.SampleDesc = sampledesc; // Sample description must match
depthStencilDesc.Usage = D3D10_USAGE_DEFAULT; // cannot be read/written by CPU
depthStencilDesc.BindFlags = D3D10_BIND_DEPTH_STENCIL;
depthStencilDesc.CPUAccessFlags = 0;
depthStencilDesc.MiscFlags = 0;

if ( FAILED ( m_pD3DDevice->CreateTexture2D( &depthStencilDesc, 0, &pWindowData->m_pDepthStencilBuffer ) ) ) {
MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to create 2D Texture for window!\n";
MxAssert( 0 );
return false;
}

// Create the depth stencil view
D3D10_DEPTH_STENCIL_VIEW_DESC descDSV;
descDSV.Format = depthStencilDesc.Format;
descDSV.ViewDimension = D3D10_DSV_DIMENSION_TEXTURE2DMS;
descDSV.Texture2D.MipSlice = 0;

if ( FAILED ( m_pD3DDevice->CreateDepthStencilView( pWindowData->m_pDepthStencilBuffer, &descDSV, &pWindowData->m_pDepthStencilView ) ) ) {
MX_LOG_MAIN << MX_LOG_FUNCTION << "Failed to create depth stencil view for window!\n";
MxAssert( 0 );
return false;
}

return true;
}




Screwed:
Screwed
Unscrewed (1 Splitter, 1 Window, 1 Empty Panel):
Non-Screwed

[Edited by - zqueezy on March 21, 2010 7:54:16 AM]

Share this post


Link to post
Share on other sites

This topic is 2859 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this  

  • Similar Content

    • By xhcao
      Does sync be needed to read texture content after access texture image in compute shader?
      My simple code is as below,
      glUseProgram(program.get());
      glBindImageTexture(0, texture[0], 0, GL_FALSE, 3, GL_READ_ONLY, GL_R32UI);
      glBindImageTexture(1, texture[1], 0, GL_FALSE, 4, GL_WRITE_ONLY, GL_R32UI);
      glDispatchCompute(1, 1, 1);
      // Does sync be needed here?
      glUseProgram(0);
      glBindFramebuffer(GL_READ_FRAMEBUFFER, framebuffer);
      glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
                                     GL_TEXTURE_CUBE_MAP_POSITIVE_X + face, texture[1], 0);
      glReadPixels(0, 0, kWidth, kHeight, GL_RED_INTEGER, GL_UNSIGNED_INT, outputValues);
       
      Compute shader is very simple, imageLoad content from texture[0], and imageStore content to texture[1]. Does need to sync after dispatchCompute?
    • By Jonathan2006
      My question: is it possible to transform multiple angular velocities so that they can be reinserted as one? My research is below:
      // This works quat quaternion1 = GEQuaternionFromAngleRadians(angleRadiansVector1); quat quaternion2 = GEMultiplyQuaternions(quaternion1, GEQuaternionFromAngleRadians(angleRadiansVector2)); quat quaternion3 = GEMultiplyQuaternions(quaternion2, GEQuaternionFromAngleRadians(angleRadiansVector3)); glMultMatrixf(GEMat4FromQuaternion(quaternion3).array); // The first two work fine but not the third. Why? quat quaternion1 = GEQuaternionFromAngleRadians(angleRadiansVector1); vec3 vector1 = GETransformQuaternionAndVector(quaternion1, angularVelocity1); quat quaternion2 = GEQuaternionFromAngleRadians(angleRadiansVector2); vec3 vector2 = GETransformQuaternionAndVector(quaternion2, angularVelocity2); // This doesn't work //quat quaternion3 = GEQuaternionFromAngleRadians(angleRadiansVector3); //vec3 vector3 = GETransformQuaternionAndVector(quaternion3, angularVelocity3); vec3 angleVelocity = GEAddVectors(vector1, vector2); // Does not work: vec3 angleVelocity = GEAddVectors(vector1, GEAddVectors(vector2, vector3)); static vec3 angleRadiansVector; vec3 angularAcceleration = GESetVector(0.0, 0.0, 0.0); // Sending it through one angular velocity later in my motion engine angleVelocity = GEAddVectors(angleVelocity, GEMultiplyVectorAndScalar(angularAcceleration, timeStep)); angleRadiansVector = GEAddVectors(angleRadiansVector, GEMultiplyVectorAndScalar(angleVelocity, timeStep)); glMultMatrixf(GEMat4FromEulerAngle(angleRadiansVector).array); Also how do I combine multiple angularAcceleration variables? Is there an easier way to transform the angular values?
    • By dpadam450
      I have this code below in both my vertex and fragment shader, however when I request glGetUniformLocation("Lights[0].diffuse") or "Lights[0].attenuation", it returns -1. It will only give me a valid uniform location if I actually use the diffuse/attenuation variables in the VERTEX shader. Because I use position in the vertex shader, it always returns a valid uniform location. I've read that I can share uniforms across both vertex and fragment, but I'm confused what this is even compiling to if this is the case.
       
      #define NUM_LIGHTS 2
      struct Light
      {
          vec3 position;
          vec3 diffuse;
          float attenuation;
      };
      uniform Light Lights[NUM_LIGHTS];
       
       
    • By pr033r
      Hello,
      I have a Bachelor project on topic "Implenet 3D Boid's algorithm in OpenGL". All OpenGL issues works fine for me, all rendering etc. But when I started implement the boid's algorithm it was getting worse and worse. I read article (http://natureofcode.com/book/chapter-6-autonomous-agents/) inspirate from another code (here: https://github.com/jyanar/Boids/tree/master/src) but it still doesn't work like in tutorials and videos. For example the main problem: when I apply Cohesion (one of three main laws of boids) it makes some "cycling knot". Second, when some flock touch to another it scary change the coordination or respawn in origin (x: 0, y:0. z:0). Just some streng things. 
      I followed many tutorials, change a try everything but it isn't so smooth, without lags like in another videos. I really need your help. 
      My code (optimalizing branch): https://github.com/pr033r/BachelorProject/tree/Optimalizing
      Exe file (if you want to look) and models folder (for those who will download the sources):
      http://leteckaposta.cz/367190436
      Thanks for any help...

    • By Andrija
      I am currently trying to implement shadow mapping into my project , but although i can render my depth map to the screen and it looks okay , when i sample it with shadowCoords there is no shadow.
      Here is my light space matrix calculation
      mat4x4 lightViewMatrix; vec3 sun_pos = {SUN_OFFSET * the_sun->direction[0], SUN_OFFSET * the_sun->direction[1], SUN_OFFSET * the_sun->direction[2]}; mat4x4_look_at(lightViewMatrix,sun_pos,player->pos,up); mat4x4_mul(lightSpaceMatrix,lightProjMatrix,lightViewMatrix); I will tweak the values for the size and frustum of the shadow map, but for now i just want to draw shadows around the player position
      the_sun->direction is a normalized vector so i multiply it by a constant to get the position.
      player->pos is the camera position in world space
      the light projection matrix is calculated like this:
      mat4x4_ortho(lightProjMatrix,-SHADOW_FAR,SHADOW_FAR,-SHADOW_FAR,SHADOW_FAR,NEAR,SHADOW_FAR); Shadow vertex shader:
      uniform mat4 light_space_matrix; void main() { gl_Position = light_space_matrix * transfMatrix * vec4(position, 1.0f); } Shadow fragment shader:
      out float fragDepth; void main() { fragDepth = gl_FragCoord.z; } I am using deferred rendering so i have all my world positions in the g_positions buffer
      My shadow calculation in the deferred fragment shader:
      float get_shadow_fac(vec4 light_space_pos) { vec3 shadow_coords = light_space_pos.xyz / light_space_pos.w; shadow_coords = shadow_coords * 0.5 + 0.5; float closest_depth = texture(shadow_map, shadow_coords.xy).r; float current_depth = shadow_coords.z; float shadow_fac = 1.0; if(closest_depth < current_depth) shadow_fac = 0.5; return shadow_fac; } I call the function like this:
      get_shadow_fac(light_space_matrix * vec4(position,1.0)); Where position is the value i got from sampling the g_position buffer
      Here is my depth texture (i know it will produce low quality shadows but i just want to get it working for now):
      sorry because of the compression , the black smudges are trees ... https://i.stack.imgur.com/T43aK.jpg
      EDIT: Depth texture attachment:
      glTexImage2D(GL_TEXTURE_2D, 0,GL_DEPTH_COMPONENT24,fbo->width,fbo->height,0,GL_DEPTH_COMPONENT,GL_FLOAT,NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, fbo->depthTexture, 0);
  • Popular Now