Jump to content

  • Log In with Google      Sign In   
  • Create Account

We're offering banner ads on our site from just $5!

1. Details HERE. 2. GDNet+ Subscriptions HERE. 3. Ad upload HERE.


Setting up DirectX issues...


Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.

  • You cannot reply to this topic
18 replies to this topic

#1 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 27 November 2013 - 12:25 AM

Hi Guys,
I have been working on some directX tutorials and am having trouble with one step. I am setting up separate functions for each step of my program, and Visual Studio crashes when it reaches my Render() function. Using the debugger I can see that my backBufferTarget_ has a value of 0x00000000. So even though I think I am initializing it in InitD3D(), it is not remembering or something. My code is below, if anyone has an advice that would be greatly appreciated. I am sure it is a simple thing I am missing.

#include<Windows.h> 
#include<memory>
#include<xnamath.h>
#include<d3d11.h>
#include<d3dx11.h>
#include<DxErr.h>

#pragma comment(lib, "winmm.lib")
#pragma comment(lib, "d3d11.lib")
#pragma comment(lib, "d3dx11.lib")
#pragma comment(lib, "dxerr.lib")

LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam);

HWND hwnd = NULL;
HINSTANCE hInstance = NULL;

ID3D11DeviceContext* d3dContext_ = NULL;
ID3D11Device* d3dDevice_ = NULL;
IDXGISwapChain* swapChain_ = NULL;
ID3D11RenderTargetView* backBufferTarget_ = NULL;

//********************
//Function prototypes*
//********************
void MessagePump(void);
bool GetFullScreen(void);
bool InitWindow(void);
void KillWindow(void);
bool InitD3D(void);
void Render(void);
bool InitScene(void);
bool InitObjects(void);

bool progFinished = FALSE;
bool progFullScreen = FALSE;

#define APP_NAME "Kenneth Game"

//************************
//Application entry point*
//************************
int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE prevInstance, LPWSTR cmdLine, int cmdShow)
{

	if (!GetFullScreen())
	{
		OutputDebugString("User abort\n");
		exit(5);
	}

	InitWindow();

	InitD3D();

	InitScene();

	while (!progFinished)
	{
		
		MessagePump(); //Check for window messages

		Render(); //Draw our graphics
	}

	KillWindow(); //Unload resources

	return 0;
}

//****************************************************************************************
//Initialise a window (full-screen or otherwise) in which our graphics will be displayed.*
//****************************************************************************************
bool InitWindow(void) 
{

	//UNREFERENCED_PARAMETER(prevInstance);
	//UNREFERENCED_PARAMETER(cmdLine);

	WNDCLASSEX wndClass = { 0 };
	wndClass.cbSize = sizeof(WNDCLASSEX);
	wndClass.style = CS_HREDRAW | CS_VREDRAW;
	wndClass.lpfnWndProc = WndProc;
	wndClass.hInstance = hInstance;
	wndClass.hCursor = LoadCursor(NULL, IDC_ARROW);
	wndClass.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
	wndClass.lpszMenuName = NULL;
	wndClass.lpszClassName = "DX11BookWindowClass";

	if (!RegisterClassEx(&wndClass))
		return false;

	RECT rc = { 0, 0, 640, 480 };
	AdjustWindowRect(&rc, WS_OVERLAPPEDWINDOW, FALSE);

	HWND hwnd = CreateWindowA("DX11BookWindowClass", "Blank Win32 Window", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, rc.right - rc.left, rc.bottom - rc.top, NULL, NULL, hInstance, NULL);

	if (!hwnd)
		return false;

	ShowWindow(hwnd, SW_SHOW);
	//UpdateWindow(hwnd);

	return true;
}

//*************************************************
//Terminate the window that was previously opened.*
//*************************************************
void KillWindow(void)
{
	MSG msg;

	while (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
	{
		DispatchMessage(&msg);
	}

	//ghAppWindow = NULL;
	ShowCursor(true);
}

//***************************
//Windows message processor.*
//***************************
LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
	PAINTSTRUCT paintStruct;
	HDC hDC;

	switch (message)
	{
	case WM_PAINT:
		hDC = BeginPaint(hwnd, &paintStruct);
		EndPaint(hwnd, &paintStruct);
		break;

	case WM_DESTROY:
		progFinished = true;
		PostQuitMessage(0);
		break;

	default:
		return DefWindowProc(hwnd, message, wParam, lParam);
	}

	return 0;
}

//**********************************************
//Process any messages that Windows has sent us*
//**********************************************
void MessagePump(void)
{
	MSG msg;

	if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
	{
		TranslateMessage(&msg);
		DispatchMessage(&msg);
	}

}

//*************************************
//Prompt selection of full screen mode*
//*************************************
bool GetFullScreen(void)
{
	int iResult;
	bool bRet = true;

	iResult = MessageBox(NULL, "Run fullscreen?", APP_NAME, MB_YESNOCANCEL | MB_ICONQUESTION);
	switch (iResult)
	{
	case IDCANCEL:
		bRet = false;
		break;
	case IDNO:
		progFullScreen = false;
		break;
	case IDYES:
		progFullScreen = true;
		break;
	case 0:
		OutputDebugString("Couldn't open MessageBox, closing");
		exit(10);
		break;
	}

	return bRet;
}

//**************************************
//Creates a hardware device in Direct3D*
//**************************************
bool InitD3D(void)
{
	D3D_DRIVER_TYPE driverType_;
	D3D_FEATURE_LEVEL featureLevel_;
	RECT dimensions;
	GetClientRect(hwnd, &dimensions);

	unsigned int width = dimensions.right - dimensions.left;
	unsigned int height = dimensions.bottom - dimensions.top;

	D3D_DRIVER_TYPE driverTypes[] =
	{
		D3D_DRIVER_TYPE_HARDWARE, D3D_DRIVER_TYPE_WARP,
		D3D_DRIVER_TYPE_REFERENCE, D3D_DRIVER_TYPE_SOFTWARE
	};

	unsigned int totalDriverTypes = ARRAYSIZE(driverTypes);

	D3D_FEATURE_LEVEL featureLevels[] =
	{
		D3D_FEATURE_LEVEL_11_0,
		D3D_FEATURE_LEVEL_10_1,
		D3D_FEATURE_LEVEL_10_0
	};

	unsigned int totalFeatureLevels = ARRAYSIZE(featureLevels);

	DXGI_SWAP_CHAIN_DESC swapChainDesc;
	ZeroMemory(&swapChainDesc, sizeof(swapChainDesc));
	swapChainDesc.BufferCount = 1;
	swapChainDesc.BufferDesc.Width = width;
	swapChainDesc.BufferDesc.Height = height;
	swapChainDesc.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
	swapChainDesc.BufferDesc.RefreshRate.Numerator = 60;
	swapChainDesc.BufferDesc.RefreshRate.Denominator = 1;
	swapChainDesc.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;
	swapChainDesc.OutputWindow = hwnd;
	swapChainDesc.Windowed = true;
	swapChainDesc.SampleDesc.Count = 1;
	swapChainDesc.SampleDesc.Quality = 0;

	unsigned int creationFlags = 0;

#ifdef _DEBUG
	creationFlags |= D3D11_CREATE_DEVICE_DEBUG;
#endif

	HRESULT result;
	unsigned int driver = 0;

	for (driver = 0; driver < totalDriverTypes; ++driver)
	{
		result = D3D11CreateDeviceAndSwapChain(0, driverTypes[driver], 0, creationFlags, featureLevels, totalFeatureLevels, D3D11_SDK_VERSION, &swapChainDesc, &swapChain_,
			&d3dDevice_, &featureLevel_, &d3dContext_);

		if (SUCCEEDED(result))
		{
			driverType_ = driverTypes[driver];
			break;
		}
	}

	if (FAILED(result))
	{
		DXTRACE_MSG("Failed to create the Direct3D device!");
		return false;
	}

	ID3D11Texture2D* backBufferTexture;

	result = swapChain_->GetBuffer(0, __uuidof(ID3D11Texture2D), (LPVOID*)&backBufferTexture);

	if (FAILED(result))
	{
		DXTRACE_MSG("Failed to get the swap chain back buffer!");
		return false;
	}

	result = d3dDevice_->CreateRenderTargetView(backBufferTexture, 0, &backBufferTarget_);

	if (backBufferTexture)
		backBufferTexture->Release();

	if (FAILED(result))
	{
		DXTRACE_MSG("Failed to create the render target view!");
		return false;
	}

	d3dContext_->OMSetRenderTargets(1, &backBufferTarget_, 0);

	D3D11_VIEWPORT viewport;
	viewport.Width = static_cast<float>(width);
	viewport.Height = static_cast<float>(height);
	viewport.MinDepth = 0.0f;
	viewport.MaxDepth = 1.0f;
	viewport.TopLeftX = 0.0f;
	viewport.TopLeftY = 0.0f;

	d3dContext_->RSSetViewports(1, &viewport);

	return true;
}

//****************************************************
// Initialise DirectX ready for us to start rendering*
//****************************************************
bool InitScene(void)
{


	
	return true;
}

//*******************************************
//Initialise the 3d objects we will be using*
//*******************************************
bool InitObjects(void)
{




	return true;
}

void Render(void)
{

	float clearColor[4] = { 0.0f, 0.0f, 0.25f, 1.0f };
	d3dContext_->ClearRenderTargetView(backBufferTarget_, clearColor);

	swapChain_->Present(0, 0);

}


Sponsor:

#2 N.I.B.   Members   -  Reputation: 1195

Like
3Likes
Like

Posted 27 November 2013 - 01:31 AM

That's the problem:

 

 


HWND hwnd = CreateWindowA("DX11BookWindowClass", "Blank Win32 Window", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, rc.right - rc.left, rc.bottom - rc.top, NULL, NULL, hInstance, NULL);

You use a local variable to store the HWND, but then when you call D3D11CreateDeviceAndSwapChain(), you use a global variable with the same name. Since the global variable was never set correctly and is still NULL, D3D11CreateDeviceAndSwapChain() fails. When you run it in debug mode, it shows the failure in the debug log.

Change the line above to:

// Initialize the GLOBAL hwnd
hwnd = CreateWindowA("DX11BookWindowClass", "Blank Win32 Window", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, rc.right - rc.left, rc.bottom - rc.top, NULL, NULL, hInstance, NULL); 

To avoid confusing global and local variables, you need a better naming convention. Specifically for HWND - you don't need it as global variable, as it's required only for initialization. Same goes for other variables. The only ones you want to keep as globals are the device and the swap-chain.


Edited by N.I.B., 27 November 2013 - 01:33 AM.


#3 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 27 November 2013 - 01:44 AM

Oh dude, thank you SO MUCH - that fixed it. I was trying for hours last night heaps of stuff. Still wrapping my head around this extra laywer of complexity (after just finishing a C++ book).

 

Thanks!



#4 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 28 November 2013 - 09:17 AM

Hi Again,
 
I come with more perils. I am now trying to add keyboard support, and like before, the program is crashing when it comes to the device I thought I have created. I am keeping my eye out for uninitiated global variables as you taught me before but cannot find the problem. The added code is:
 

//**********************
//DirectInput variables*
//**********************
#define KEYDOWN( name, key ) ( name[key] & 0x80 )
LPDIRECTINPUT8 directInput_ = NULL;
LPDIRECTINPUTDEVICE8 keyboardDevice_ = NULL;
char keyboardKeys_[256];
char prevKeyboardKeys_[256];

For the Initialization routine (which is called before Update() and Render():

bool InitInput(void)
{
    HRESULT result;

    ZeroMemory(keyboardKeys_, sizeof(keyboardKeys_));
    ZeroMemory(prevKeyboardKeys_, sizeof(prevKeyboardKeys_));

    result = DirectInput8Create(hInstance, DIRECTINPUT_VERSION, IID_IDirectInput8, (void**)&directInput_, 0); //Initialize DirectInput8

    if (FAILED(result))
    {
        return false;
    }

    result = directInput_->CreateDevice(GUID_SysKeyboard, &keyboardDevice_, 0);

    if (FAILED(result))
    {
        return false;
    }

    result = keyboardDevice_->SetDataFormat(&c_dfDIKeyboard);

    if (FAILED(result))
    {
        return false;
    }

    result = keyboardDevice_->SetCooperativeLevel(ghHwnd, DISCL_FOREGROUND | DISCL_NONEXCLUSIVE);

    if (FAILED(result))
    {
        return false;
    }

    result = keyboardDevice_->Acquire();

    if (FAILED(result))
    {
        return false;
    }

    return true;
}

And for the Update() routine:

//******************************
//Get current state of Keyboard*
//******************************
void Update(void)
{
	float fElapsed;
	float rotZ = 0;
	float fY = 0.0f;

	keyboardDevice_->GetDeviceState(sizeof(keyboardKeys_), (LPVOID)&keyboardKeys_);

	if (GetAsyncKeyState(VK_ESCAPE))
	{
		PostQuitMessage(0);
	}

	// Button up event.
	if (KEYDOWN(prevKeyboardKeys_, DIK_DOWN) && !KEYDOWN(keyboardKeys_, DIK_DOWN))
	{
		fY -= 0.1f;
	}


	if (KEYDOWN(prevKeyboardKeys_, DIK_UP) && !KEYDOWN(keyboardKeys_, DIK_UP))
	{
		fY += 0.1f;
	}

	memcpy(prevKeyboardKeys_, keyboardKeys_, sizeof(keyboardKeys_));

	gfTimeScale = 0.001f;
	fElapsed = GetElapsedTime();
	rotZ += fElapsed;
}

 
It is crashing at keyboardDevice_->GetDeviceState(sizeof(keyboardKeys_), (LPVOID)&keyboardKeys_);

 

The debugger shows keyboardDevice_ becomes a 0x00000000 (similar to before). Again this is adapting code that works when it was done in the way the book shows.

 

Again any help is greatly appreciated.

 

Thanks


Edited by SteveHatcher, 28 November 2013 - 09:21 AM.


#5 Samith   Members   -  Reputation: 2260

Like
1Likes
Like

Posted 28 November 2013 - 10:07 AM

The debugger shows keyboardDevice_ becomes a 0x00000000 (similar to before). Again this is adapting code that works when it was done in the way the book shows.

After a quick glance at your code in not sure what's wrong, but I did notice one thing: you don't seem to ever check the result of your Init functions. In InitInput you return false if anything failed, but then you never check if InitInput returns true or not (I'm assuming, based on the code in the original post).

You should check the return values of your Init functions, and at the very least log something if they're false. It's possible that keyboardDevice_ never initialized properly (and thus was always NULL) but you won't catch that until you're update loop. You want to try and find errors as soon as possible! Crash early and crash often, as the saying goes.

EDIT: Looked at your code again. Looks like hInstance is uninitialized. You can get hInstance from WinMain.

Edited by Samith, 28 November 2013 - 10:12 AM.


#6 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 29 November 2013 - 01:06 AM

Thank you very much! In my main I changed it to:

	if (!InitInput())
	{
		OutputDebugString("  Input initialisation failed\n");
		exit(5);
	}

and could see it was failing here. You were spot on about hInstance. The way I got it was with

hInstance = GetModuleHandle(NULL); 

Do you think that's okay? Or is another better way to do it?

 

Thanks heaps!



#7 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 29 November 2013 - 06:36 AM

Hi Guys..

 

Stuck yet again. This time I am simply trying to display my triangle slightly rotated.

 

I have added some vertices:

VertexPos gVertices[] = 
{
	XMFLOAT3(0.5f, 0.5f, 0.5f), 
	XMFLOAT3(0.5f, -0.5f, 0.5f),
	XMFLOAT3(-0.5f, -0.5f, 0.5f)
};

which come into play here in InitObjects(void)

	ZeroMemory(&resourceData, sizeof(resourceData));
	resourceData.pSysMem = gVertices;
	d3dResult = d3dDevice_->CreateBuffer(&vertexDesc, &resourceData, &vertexBuffer_);

	D3D11_BUFFER_DESC constDesc;
	ZeroMemory(&constDesc, sizeof(constDesc));
	constDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
	constDesc.ByteWidth = sizeof(XMMATRIX);
	constDesc.Usage = D3D11_USAGE_DEFAULT;

	d3dResult = d3dDevice_->CreateBuffer(&constDesc, 0, &mvpCB_);

with the final Render() function as

void Render(void)
{
	if (d3dContext_ == 0) //Checks that the Direct3D context is valid. 
		return;


	float clearColor[4] = { 0.0f, 0.0f, 0.25f, 1.0f };
	d3dContext_->ClearRenderTargetView(backBufferTarget_, clearColor);
	unsigned int stride = sizeof(VertexPos);
	unsigned int offset = 0;

	//Setting up the input assembly
	d3dContext_->IASetInputLayout(inputLayout_); 
	d3dContext_->IASetVertexBuffers(0, 1, &vertexBuffer_, &stride, &offset); 
	d3dContext_->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST); 
	d3dContext_->VSSetShader(solidColorVS_, 0, 0);
	d3dContext_->PSSetShader(solidColorPS_, 0, 0);


	XMMATRIX view = XMMatrixIdentity();
	XMMATRIX projection = XMMatrixOrthographicOffCenterLH(0.0f, 800.0f, 0.0f, 600.0f, 0.1f, 100.0f); //1a. Creates an orthographic projection matrix using LHS. Return value is a XMMATRIX structure where the resulting projection matrix is placed.
	XMMATRIX vpMatrix_ = XMMatrixMultiply(view, projection);

	XMMATRIX translation = XMMatrixTranslation(10.0f, 10.0f, 10.0f);
	XMMATRIX rotationZ = XMMatrixRotationZ(30.0f);
	XMMATRIX scale = XMMatrixScaling(0.0f, 0.0f, 0.0f);
	XMMATRIX TriangleWorld = translation * rotationZ;

	XMMATRIX mvp = TriangleWorld*vpMatrix_*translation;
	mvp = XMMatrixTranspose(mvp);

	d3dContext_->UpdateSubresource(mvpCB_, 0, 0, &mvp, 0, 0);
	d3dContext_->VSSetConstantBuffers(0, 1, &mvpCB_);

	d3dContext_->Draw(3, 0); 
	swapChain_->Present(0, 0);
}

No matter what I change in the XMMatrixRotationZ or XMMatrixTranslation, my triangle stays the same. Its as if since the buffer is created I am not altering it at all.

 

I have tried many combinations of matrix multiplication ways and large numbers to no avail. It is as if the mvp matrix is having no effect on the final image. Thank you for your time - I have spent many hours trying to figure this out and only come here as a last resort. I find the best way to learn is trying to figure out broken code...


Edited by SteveHatcher, 29 November 2013 - 06:37 AM.


#8 unbird   Crossbones+   -  Reputation: 5585

Like
1Likes
Like

Posted 29 November 2013 - 07:49 AM

And what does your vertex shader do ? Pass-through ? Show us, please.



#9 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 29 November 2013 - 07:55 AM

Not 100% sure what you mean, but my vertex shader is created here:

bool InitObjects(void)
{
	
	DWORD shaderFlags = D3DCOMPILE_ENABLE_STRICTNESS;

#if defined( DEBUG ) || defined( _DEBUG )
	shaderFlags |= D3DCOMPILE_DEBUG;
#endif

	ID3DBlob* errorBuffer = 0;
	ID3DBlob* vsBuffer = 0;

	//bool compileResult = CompileD3DShader("SolidGreenColor.fx", "VS_Main", "vs_4_0", &vsBuffer); //Loads vertex shader from the text file and compiles it into byte code. 
	//bool compileResult = D3DX11CompileFromFile("SolidGreenColor.fx", 0, 0, "VS_Main", "vs_4_0", shaderFlags, 0, 0, &vsBuffer, &errorBuffer, 0);

	HRESULT result;
	result =  D3DX11CompileFromFile("SolidGreenColor.fx", 0, 0, "VS_Main", "vs_4_0", shaderFlags, 0, 0, &vsBuffer, &errorBuffer, 0);

	if (FAILED(result))
	{
		if (errorBuffer != 0)
		{
			OutputDebugStringA((char*)errorBuffer->GetBufferPointer());
			errorBuffer->Release();
		}

		return false;
	}

	HRESULT d3dResult;

	d3dResult = d3dDevice_->CreateVertexShader(vsBuffer->GetBufferPointer(), vsBuffer->GetBufferSize(), 0, &solidColorVS_);

	if (FAILED(d3dResult))
	{
		if (vsBuffer)
			vsBuffer->Release();

		return false;
	}

	D3D11_INPUT_ELEMENT_DESC solidColorLayout[] = //Used to describe the vertex latout of a vertex streucture. (msdn). 
	{
		{ "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 } //3b
	};

	unsigned int totalLayoutElements = ARRAYSIZE(solidColorLayout);

	d3dResult = d3dDevice_->CreateInputLayout(solidColorLayout, totalLayoutElements, //3c The input layout uses the type of ID3D11InputLayout. Created with a call to the D3D device function CreateInputLayout. 
		vsBuffer->GetBufferPointer(), vsBuffer->GetBufferSize(), &inputLayout_);

	vsBuffer->Release();

	if (FAILED(d3dResult))
	{
		return false;
	}

	ID3DBlob* psBuffer = 0;

	result = D3DX11CompileFromFile("SolidGreenColor.fx", 0, 0, "PS_Main", "ps_4_0", shaderFlags, 0, 0, &psBuffer, &errorBuffer, 0);

	if (FAILED(result))
	{
		if (errorBuffer != 0)
		{
			OutputDebugStringA((char*)errorBuffer->GetBufferPointer());
			errorBuffer->Release();
		}

		return false;
	}

	d3dResult = d3dDevice_->CreatePixelShader(psBuffer->GetBufferPointer(), psBuffer->GetBufferSize(), 0, &solidColorPS_);

	psBuffer->Release();

	ZeroMemory(&vertexDesc, sizeof(vertexDesc));
	vertexDesc.Usage = D3D11_USAGE_DEFAULT;
	vertexDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
	vertexDesc.ByteWidth = sizeof(VertexPos)* 3;

	ZeroMemory(&resourceData, sizeof(resourceData));
	resourceData.pSysMem = gVertices;
	d3dResult = d3dDevice_->CreateBuffer(&vertexDesc, &resourceData, &vertexBuffer_);

	D3D11_BUFFER_DESC constDesc;
	ZeroMemory(&constDesc, sizeof(constDesc));
	constDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
	constDesc.ByteWidth = sizeof(XMMATRIX);
	constDesc.Usage = D3D11_USAGE_DEFAULT;

	d3dResult = d3dDevice_->CreateBuffer(&constDesc, 0, &mvpCB_);

	if (FAILED(d3dResult))
	{
		return false;
	}

	return true;

}

My goal is to modify the triangle in world space so the rotation or translation matrices have an effect on it. Thanks for your time.


Edited by SteveHatcher, 29 November 2013 - 07:56 AM.


#10 unbird   Crossbones+   -  Reputation: 5585

Like
1Likes
Like

Posted 29 November 2013 - 07:58 AM

Nope, I meant the HLSL, the source code of your vertex shader: VS_Main.



#11 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 29 November 2013 - 08:00 AM

Oh Sorry, Im guessing you mean the .fx file that D3Dx11CompileFromFile is grabbing?

 

It is:

float4 VS_Main( float4 pos : POSITION ) : SV_POSITION
{
    return pos;
}


float4 PS_Main( float4 pos : SV_POSITION ) : SV_TARGET
{
    return float4( 0.0f, 1.0f, 0.0f, 1.0f );
}

A solid green shader as far as I am aware.



#12 cdoubleplusgood   Members   -  Reputation: 844

Like
2Likes
Like

Posted 29 November 2013 - 08:08 AM

Your vertex shader just passes the unchanged vertex positions. To apply any transformation, e.g. rotation, you need to multiply with the transformation matrix you assigned to the constant buffer.



#13 unbird   Crossbones+   -  Reputation: 5585

Like
1Likes
Like

Posted 29 November 2013 - 08:09 AM

Precisely. Yeah, that's a pass-through vertex shader, the position doesn't change at all wink.png

It should look something like this:
 
cbuffer VSParameters : register(b0)  // deliberately assigning slot 0 !
{
	matrix WVP;
};

float4 VS_Main( float4 pos : POSITION ) : SV_POSITION
{
	return mul(position, WVP);
}
Also, you probably want to rotate (and/or scale) first, then translate. Order of multiplication matters with matrices:

XMMATRIX TriangleWorld = rotationZ * translation;


#14 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 29 November 2013 - 08:14 AM

Okay, thanks guys. I am still slowly digging my way through the literature.

 

Is there a way to create a simple shader like this but entirely in a struct, or class of my definition so it does not need a separate .fx file? If so, what function do I use instead of the D3Dx11CompileFromFile?

 

I hope my question makes sense. Thanks. you guys are extremely helpful and awesome!



#15 unbird   Crossbones+   -  Reputation: 5585

Like
1Likes
Like

Posted 29 November 2013 - 08:25 AM

Not quite sure what you mean. You can have several shaders in the same file (like you already do for both vertex and pixel shader). And there are compile functions which take source code directly, without the detour of a file, e.g. D3DX11CompileFromMemory or alternatively the newer compile function D3DCompile.

Put your HLSL source as a static string in your cpp file and feed it to one of those functions.

(Alternatively one could even let the command line compiler fxc spit out compiled binaries as a hex array source code, with the option /Fh. This way no runtime compilation is needed)

#16 cdoubleplusgood   Members   -  Reputation: 844

Like
1Likes
Like

Posted 29 November 2013 - 12:51 PM


Is there a way to create a simple shader like this but entirely in a struct, or class of my definition so it does not need a separate .fx file? If so, what function do I use instead of the D3Dx11CompileFromFile?

No, that doesn't make much sense.

Of course you could include the source of your HLSL file as string constant in your code, but this is not very common.

If you don't want to compile your shaders at runtime, you can do it offline using the fxc.exe command line compiler. Take this:

http://msdn.microsoft.com/en-us/library/windows/desktop/bb509709%28v=vs.85%29.aspx

What I do is this: I let fxc.exe create an header file (command line option /Fh). This .h file contains a byte array with the compiled shader code that can be passed to e.g. ID3D11Device::CreateVertexShader.



#17 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 29 November 2013 - 10:55 PM

Just out of interest, why do they have them in a separate file? I can't see the advantage of this as opposed to having them in a header file and just including it?

 

Thanks



#18 cdoubleplusgood   Members   -  Reputation: 844

Like
1Likes
Like

Posted 30 November 2013 - 05:31 AM

I'm not sure if I get the idea behind your question. You have a project with mixed languages: C++ and HLSL. They have different compilers. Why would you mix the languages in a single file?



#19 SteveHatcher   Members   -  Reputation: 479

Like
0Likes
Like

Posted 01 December 2013 - 04:02 AM

I'm not sure if I get the idea behind your question. You have a project with mixed languages: C++ and HLSL. They have different compilers. Why would you mix the languages in a single file?

That answers my question, didn't click about it being a different language lol. Thanks






Old topic!
Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.



PARTNERS