Public Group

DX12 DirectX11 or DirectX12?

Recommended Posts

Hello!

I'm having a difficult time deciding if I'm going to learn DirectX11 or DirectX12. Since I want to get a job in game development when I finish my studies, it feels like I would leave a better impression on the company if I've created something in DirectX12, since that's the more performant API. At the same time, DirectX12 is a bit frustrating sometimes, because it feels like every struct I fill in constists on another struct that consists of another struct and some parts just feel overly complicated. I've used DirectX11 for a while, and it feels a bit easier to use, but at the same time I don't want to base my decision only on what's more easy, but also what's better for my carrer.

So basically, this topic boils down into 2 different questions:

1. Should I learn DirectX11 or DirectX12 in regards to what's better for my future career?
2. Is really DirectX12 that much more difficult than DirectX11, or is it a combination of me being unfimiliar with the new names/concepts, and/or me overcomplicating things?

In regards to point 1, my aim is to produce some kind of hobby projects, either a lightweight game engine, or some standalone demos, that I can use as a portfolio when I search for a future job. Is this a good approach or am I thinking entirely wrong? Would a company find it more impressing that I've used an existing engine to write a small game, or would they find it more impressing that I've written a small engine in DirectX12?

In regards to point 2, I don't find the whole CPU-GPU parallelism so difficult to understand, but rather the way of initializing everything and knowing what I should initialize and the best way to do it. Also there're some concepts that I think are overly complicated, either because I don't understand it, or well because they're overly complicated. This is easier explained with a few examples.

One example is the new pipeline state object (PSO) in DirectX12 that's confusing me a bit. At first I thought the idea of setting up a struct rather than using loads of function calls was a great idea, but the further I tried it out I noticed that now I had to set up things both in the PSO and with the functions. For example, I can set the primitive topology in the PSO:

pipelineStateDesc.PrimitiveTopologyType = D3D12_PRIMITIVE_TOPOLOGY_TYPE_TRIANGLE;

But then in my render function I still need set the primitive topology individually:

m_commandList->IASetPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST);

Same applies to the root signature:

pipelineStateDesc.pRootSignature = m_rootSignature;

And then in my render function I need to do it again:

m_commandList->SetGraphicsRootSignature(m_rootSignature);

And then there's also the whole part of filling in struct after struct to describe CBV/SRV/UAV inputs to a shader, and then in the render function I still have to call a function:

m_commandList->SetGraphicsRootDescriptorTable(0, m_constantBufferHeap->GetGPUDescriptorHandleForHeapStart());

Also the whole part of setting up differend heaps for different descriptors feels so unnecessarily complicated.

So to get to the point instead of complaining about it, is it supposed to be like this or am I doing something very wrong here? And while I understand that this might be a difficult question to answer, is it actually this complicated, or does it just feel like that because it's new concepts and names for me?

Thank you for taking the time to read this and thank you in advance for helping me out.

Share on other sites

DirectX11 is easier to learn, because the library does more for you, but the performance is mildly worse. I would suggest that if you don't already have a very good grounding in computer graphics including modern render pipelines, shaders, etc. (and it sounds like you don't?) then it's probably a better idea to start in DirectX11.

As to what will impress potential employers more between a game in an engine and building your own renderer? Well, who knows. It's likely to vary depending on the prejudices of whoever interviews you. But, in general, it depends to a good extent on what you want to do. Do you want to work on low level engine stuff? Then demonstrating you can do it at the lowest level is a good thing, but if you want to write more gameplay stuff then you're probably better working with an existing engine. Most professional studies are using these engines these days anyway, so demonstrable experience is not a bad thing.

Share on other sites

I understand. Will give it some more thought, but maybe I will stick to DirectX 11 then. But at the same time, I'm worried that if I learn DirectX 11 now, then by the time I finish my studies, DirectX 11 will not even be attractive anymore. At the same time, I'm worried that DirectX 12 will drag me into a lot of bugs that will make me spend more time on sorting it out rather than implementing features.

I'm very thankful for your reply, but as you see, I'm still unsure of what to do 😟

Also, do you know why some things in DX12 seem to be required to set twice? For example, when I create the PSO, I set the root signature:

pipelineStateDesc.pRootSignature = m_rootSignature;

And then in my render function I need to set it again:

m_commandList->SetPipelineState(m_pipelineState);
m_commandList->SetGraphicsRootSignature(m_rootSignature);

If I don't set it, I get debug warnings from DirectX. The MSDN documentation states this:

Quote

The root signature set on a command list or bundle must also match the currently set PSO at Draw/Dispatch; otherwise, the behavior is undefined.

Which really makes me wonder, if they need to match, why are we forced to set it twice?

Granted I'm still a noob, but this makes no sense, especially since their aim was to make it more efficient, settings things twice doesn't seem very efficient... 🤔

Share on other sites

Thanks for the detailed answer Hodgeman.

1 hour ago, Hodgman said:

if I had a candidate who claimed proficiency in D3D12 without knowing D3D11

Well, I have learned a bit of DX11 earlier. Things like vertex shaders, geometry shaders, pixel shaders, compute shaders, append buffers, consume buffers, render targets, constant buffers, instancing, billboarding, dynamic vertex buffers, textures, normal maps, height maps, shader resource views, unordered access views. I think that's pretty much it. So with that in mind, would you say that it's better if I continue with DX11 and learn more, or do you think that's enough to take the step over to DX12?

1 hour ago, Hodgman said:

What kind of gamedev role are you looking for?

Hmm, difficult question, since all of them sounds fun and interesting. I think the most fun would be to either work on the companys game engine itself, like a rendering architect or something like that, or to work with a game title, either as a programmer implementing features, or even as a designer. If I want to widen the range of possible roles that I can be recruited for, what do you think is the right way to go, using an existing game engine or creating a small engine?

Share on other sites
1 hour ago, VAPOV said:

either as a programmer implementing features, or even as a designer. If I want to widen the range of possible roles that I can be recruited for

Be careful about that. Most studios are looking for one or the other position and if potential candidate says I can be a programmer or designer, I would be leery to hire. Pick the role you want to pursue and work towards that goal. If I may assume, you are early in your professional life, meaning not allot of experience will add more blocks and friction, adding two vastly different  disciplines will not help you. If you get a job as a programmer, nothing stops you in the future to pursue that, but still will be a long track.

2 hours ago, VAPOV said:

I think the most fun would be to either work on the companys game engine itself, like a rendering architect or something like that

Most studios that have that kind of work usually have more senior engineers to work on it. As a junior programmer, chances will be lower for you to get that kind of position.

just my 2c.

• 10
• 10
• 12
• 10
• 33