0

Bleh, that title seemed a bit too long to me...couldn't really think of a shorter way of wording it though.

Right, I'll try and encapsulate the problem as best I can. I'm currently, as per the title, attempting to create a c++/DirectX multiple windowed swap chained system which can handle differing resolutions for each window.

I have the whole thing working EXCEPT for resizing of the master window. If it's larger then the rest of them or indeed, the same size, everything works fine. All of the child windows scale appropriately, even assigning them stupid resolutions like 10x800.

The issue comes when the master window is smaller then any of the other windows; it appears to crop the display picture of those subsequent child windows in accordance with the size of the master window.

For example:
Window 1 = 500x500
Window 2 = 1000x1000

The second window will only draw to the top left quarter of the window yet it appears as though it has stretched appropriately; only the top quarter of the PICTURE would be drawn in the quarter of the window. So it scales as though it's setup correctly. I have a light blue background for a non-directX clear background and dark blue for the DirectX clear command. In this instance, dark blue will only be drawn in the top-left so DirectX seems not to want to touch any portion of a window which would not fall within the boundaries of the master window.

I have checked all of my parameters going in but fear that is not where the issue lies. One work around could be to supply a large master window yet simply have it hidden from the user, thus all child windows could scale upto it but to be that feels more like putting a band-aid over the issue rather then tackling it properly.

Creation of the device:

//******************************************************//
	//	         Create the DX9 device.	          //
	//******************************************************//
	d3d = Direct3DCreate9(D3D_SDK_VERSION);
	if(d3d == NULL)
		return DDIS_ERR_INIT_CREATE_D3D9;

	//Create d3d device connections with the default graphics adapter.
	d3dDevice = NULL;

	//******************************************************//
	//		Windowed mode setup.		 //
	//  This utilizes swap chains for faster rendering for	 //
	//	  potentially any number of windows.		 //
	//******************************************************//
	else{
		//Create the master display first.
		if(FAILED(d3d->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, NULL, D3DCREATE_HARDWARE_VERTEXPROCESSING, &displayHandles.at(0).d3dpp, &d3dDevice)))
			return DDIS_ERR_INIT_WNDCREATEDEVICE;

		//With parameters and windows created, create swap chains relative to DISPLAY_HANDLEs.
		for(int x = 0; x < (int)displayHandles.size(); x++){
			displayHandles.at(x).swapChain = NULL;

			//For the first display, just call up the swap chain.
			if(x == 0){
				if(FAILED(d3dDevice->GetSwapChain(0, &displayHandles.at(x).swapChain)))
					return DDIS_ERR_INIT_WNDGETSWAPCHAIN;
			}

			//For all preceeding displays, call their presentation parameters.
			else{
				if(FAILED(d3dDevice->CreateAdditionalSwapChain(&displayHandles.at(x).d3dpp, &displayHandles.at(x).swapChain)))
					return DDIS_ERR_INIT_WNDCREATESWAPCHAIN;
			}

			if(FAILED(displayHandles.at(x).swapChain->GetBackBuffer(0, D3DBACKBUFFER_TYPE_MONO, &displayHandles.at(x).backBuffer)))
				return DDIS_ERR_INIT_WNDGETBACKBUFFER;
		}
	}

	return DDIS_OK;

Beginning of the scene:

//Set all appropriate rendering device properties.
				if(FAILED(d3dDevice->SetRenderTarget(0, displayHandles.at(displayIdentifier).backBuffer)))
					return DDIS_ERR_BEGC_WNDSETRENDERTARGET;
				if(FAILED(d3dDevice->Clear(0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(0,155,155), 1.0f, 0)))
					return DDIS_ERR_BEGC_WNDCLEAR;
				if(FAILED(d3dDevice->BeginScene()))
					return DDIS_ERR_BEGC_WNDBEGINSCENE;

				//Inform the class of the displayIdentifier.
				currentActiveDevice = displayIdentifier;

Ending the scene:

//If windowed, end the scene, draw the swapChain and empty the buffers.
			if(FAILED(d3dDevice->EndScene()))
				return DDIS_ERR_ENDC_WNDENDSCENE;
			if(FAILED(displayHandles.at(currentActiveDevice).swapChain->Present(NULL, NULL, displayHandles.at(currentActiveDevice).wndHandle, NULL, 0)))
				return DDIS_ERR_ENDC_WNDPRESENT;
			if(FAILED(displayHandles.at(currentActiveDevice).backBuffer->Release()))
				return DDIS_ERR_ENDC_WNDRELEASE;
			return DDIS_OK;

Alas I fear a quick fix may be too optimistic but if anyone has come across this issue before, please let me know. More information can be provided but displaying of the whole class seems a little pointless as it's mixed in with a lot of other stuff (none of which is active during windowed mode).

Thanks for your time.

Edited by kirennian: n/a

2
Contributors
6
Replies
7
Views
7 Years
Discussion Span
Last Post by Ketsuekiame
0

Okay so it appears the clear message is in fact clearing the whole window; the plot thickens. It would appear it's the object drawing which may well turn out to be the issue. I'll report back here when I figure out the problem.

0

I came across a similar situation before but using OpenGL. Turned out to be the fact that the Viewport remained the same size as the primary window and hence only drew that size into the top left of the secondary window.

I don't know if that will help you though.

0

I came across a similar situation before but using OpenGL. Turned out to be the fact that the Viewport remained the same size as the primary window and hence only drew that size into the top left of the secondary window.

I don't know if that will help you though.

Cheers for the response. :)

I thought I'd got it from that but alas it doesn't seem to be the issue. Each of the screens have the correct viewport; I tested by creating 3:

1:800x600
2:1024x768
3:640x480

The first was correct, the third scaled correctly but the 2nd simply ignored to right/bottom bounds and used the first windows instead; it scaled correctly as if the drawn surface was scaled for the 1024x768, it just didn't draw it all. I then tried setting the X/Y coordinates of the viewport to 100x100; each of the displays did this correctly except for the second which instead used x:100-600, y:100-800 as its bounds.

I'm confused as I at least thought that might have shifted the viewport down and right instead of simply clipping it...

Interestingly, setting the viewport to 1000x1000, the first screen reacted correctly, the second still clipped into the 800x600 area but instead scaled for such a resolution and the third, overstretched itself.

I'm wondering if there is a window 'stretch' flag I can declare for each of the DirectX drawplanes somehow.

1

Unfortunately I'm not too heavily into DirectX, but This may help

Unfortunately that's about as helpful as I can be on DirectX ^^

Edited by Ketsuekiame: n/a

Votes + Comments
Problem solved, nice one! :)
0

Unfortunately I'm not too heavily into DirectX, but This may help

Unfortunately that's about as helpful as I can be on DirectX ^^

No unfortunately about it mate; it just goes to show, inspiration can come from anywhere and even those who say they don't know anything about a topic can come up with gems of advice.

I thought about this as a solution before but it seemed to create redundant data which I didn't like. I basically created a master swap chain, linked it to no backbuffer, no window, just set it up as a maximum resolution potential for any monitor connected and created every window as its child, including the primary focus window.

The result? I can create any window of any size (upto that maximum), I no longer have to invalidate and restore the program upon the primary window changing size, I can merely remove and recreate a single swap chain, causing a massive jump in performance during system commands being issued to the window.

Much appreciated bud, that's been bugging me for a little while... and as for the redundant data? I simply don't call the swapchain so it's a matter of bytes sitting idle in the VRAM (from what I gather) and if I don't bother it during the programs runtime, it doesn't bother me! :D

Edited by kirennian: n/a

This question has already been answered. Start a new discussion instead.
Have something to contribute to this discussion? Please be thoughtful, detailed and courteous, and be sure to adhere to our posting rules.