31

It really depends on the technique. In a forward render you often have one shader for every different material type. In AAA games that use this technique shaders are often generated from a set of options on the material which an artist can set. This can lead to hundreds of shaders(1). But lets say generally the number of shaders is in the order of 40 In a ...


23

Yes, a game engine will in general have a variety of different shaders. The typical pattern is: While initializing the engine and loading the game world, prepare all the shaders you will use for rendering. By "prepare" I mean load them into memory, compile them if necessary, and do all the ID3D11Device::CreatePixelShader and similar calls to get ...


15

I think the main optimization you can make, is based on the fact that not every cube will actually need all 24 vertices. In fact, the only cubes that need 24 vertices are the ones that are floating in midair, which is probably a rare occurrence. In general, only generate quads for the faces that are in contact with air. This means that if two cubes are ...


15

Yes. You can initialize the Direct3D device using D3D11CreateDevice, which requires no window. You simply do not create a swap chain at all. You can still create offscreen render targets and draw to them in the usual way. Instead of calling Present on the swap chain, you can call ID3D11DeviceContext::Flush to kick the GPU with the work you've queued up. ...


11

There's a good presentation about this: Don't Throw It All Away: Efficient Buffer Management by John McDonald at NVIDIA. It covers various topics, but on the subject of your question, the general advice is to create buffers with dynamic usage and use Map() with D3D11_MAP_WRITE_DISCARD, when the data needs to be updated frequently (like every frame, or ...


10

The Sample method accepts a UV coordinate (where the texture covers the [0, 1] range), does mipmap selection based on the UV derivatives, applies addressing modes (clamp, wrap, border) and does filtering (bilinear, trilinear, aniso). The Load method accepts a texel coordinate in the [0, textureWidth - 1] x [0, textureHeight - 1] range, and the desired mip ...


9

If you only need per-face normals, and if your texcoords for a face are strictly 0/0, 0/1, 1/0, 1/1 (or similar to suit your layout) then you can construct a cube with 8 verts and either 30 (strip with restart) or 36 (list) indexes. Fetch the normals and texcoords using a constant array lookup based on SV_VertexID in your vertex shader. Doing this means ...


8

You have to create the threads yourself, using your threading library of choice (boost, C++11 async, Windows threads, etc). The idea is that you will create several threads and split up your CPU rendering work amongst them. Each thread uses a D3D11 deferred context to accumulate all the D3D11 commands (state changes, draw calls, etc.) it wants to execute. ...


8

The FBX documentation is painful at times, and this is definitely one of them. There are two ways I've used to access animation data. The first is used in the ImportScene sample that comes with the SDK, and it's the way you seem to be trying to do things. In your sample, now that you have a valid lAnimCurve, you would need to query the number of keyframes ...


8

No, at least in D3D11 it is not possible to change the size of a buffer or texture after it's been allocated. You would have to release the old buffer and create a new one (which is inadvisable to do often, as it can hurt performance). It's okay to only use part of a vertex buffer, so if you know the maximum size your data will be, I'd allocate the buffer ...


8

The "DirectX" project templates are for Windows Store Apps / Windows Phone Apps. So I assume it has to do with the version of VS Express you are using (Desktop). However, you don't need anything special to write traditional desktop apps. You just need to create a Win32 Application and include the DX11 headers in your code


7

Typically, branching of any kind (switches, if-statements, loops with non-constant iterations) are best avoided. This is mildly true on the PC (not enough to be worth worrying about at all outside of very tight inner loops), especially true on some general-purpose CPUs like the 360's Xenon (common hardware that makes indirect references on branches ...


7

Yes, you can do this with d3d11 shader reflection. Here is some code showing how to iterate over a constant buffer, as well as grab all the values within the cbuffer. This doesn't require you to know anything about the shader. ID3D11ShaderReflection* reflection = NULL; D3D11Reflect(description->buffer, description->length, &reflection); ...


7

Use several constant buffers and group variables together based on how often they change. If your variables are fairly static ( or just huge ) you may be better off converting values into a texture and extracting them in the shader.


7

The range [-1 ; 1] x [-1 ; 1] x [0 ; 1] mentioned in the tutorial refers to the canonical view volume. It is the final coordinate space vertex data gets mapped to before everything is rasterized to your screen. To understand what exactly this means, it helps to take a look at what a rendering pipeline typically looks like. Coordinate spaces A coordinate ...


6

Thanks for the answers on this, they are very helpful. I'll add an answer to my own question because I've moved on a bit from there. In the end I realized that perhaps wanting to entirely separate the shaders from the drawable items was a mistake. They are fundamentally coupled in "real life" so it's perhaps not an issue that they are in the design. For ...


6

SV_Position in the pixel shader gives you the the center point of the pixel being shaded, in a [0, bufferWidth] x [0, bufferHeight] range. (It can also be used in centroid mode with MSAA to get the centroid of the covered samples.) This value can be passed directly to Texture2D.Load to retrieve the corresponding pixel from a texture the same size as the ...


6

Instead of D3DXVec3Unproject() use XMVector3Unproject(). It accpet float parameters for viewport: XMVECTOR XMVector3Unproject( [in] XMVECTOR V, [in] float ViewportX, [in] float ViewportY, [in] float ViewportWidth, [in] float ViewportHeight, [in] float ViewportMinZ, [in] float ViewportMaxZ, [in] XMMATRIX Projection, [in] XMMATRIX ...


6

System memory also loses power during hibernation, as the system is completely powered off during hibernate. Windows deals with both system memory and video memory the same way: it dumps them to disk. Hence, it is only copying out video memory when necessary, when hibernation is invoked. If you meant stand-by mode, where the system is put into low-power ...


6

You need to make sure that any variable you use within the constant buffer does not cross a 16 byte alignment boundary, or you won't be able to access it from the shader. For example, you could have a constant buffer that looks like this: struct constant_buffer { XMFLOAT4X4 wvp; // 64 bytes -> 16 byte aligned = OK XMFLOAT3 position; // 12 ...


Only top voted, non community-wiki answers of a minimum length are eligible