domingo, 31 de marzo de 2013

Basic Direct3D11

Once the window is created with the Win32 API, we have to initialize Direct3D11 enrolling the D3D rendering system to the window and render the scene to the window.

Simple D3D11 application (MSDN)

For this we have to include "d3d11.h" and "d3dx11.h".

Initialization

To initialize D3D11 we have to create a D3D11 device.
To create a D3D11 device we need to create COMs (component object model). It is used by D3D11 to be language independent and backward compatible (D3D10 and 9). These objects aren't created and destroyed with the C++ "new" and "delete" keyword respectively. (To destroy it we have to use the "Realease" method for each COM). COM are prefixed with a capital i, 'I'. The COM for a 2d texture is called ID3D11Texture2D.

Specifically we have to create (COM):

1. Render Target ( ID3D11RenderTargetView ): For some pipeline stages we are going to use a texture. D3D requires that we create a resource view in the moment of initialization for the texture. For now, we are going to use only the ID3D11RenderTargetView resource view. Basically, this is the texture for the backbuffer. (Where we process the scene).

2. Swap Chain ( IDXGISwapChain ): It defines two buffers (or more). Front and Back buffers. The COM uses those buffers to avoid flickering in animation.

3. Context ( ID3D11DeviceContext ): It binds the resources to the graphics pipeline (see pipeline stages).

4. Device ( ID3D11Device ): It is used to allocate all the resources.


Basically to initialize direct3d we have to do the following steps:

1. Create device and context.
2. Describe the swap chain.
3. Create the swap chain.
4. Create a render target view to the swap chain's backbuffer,
5. Bind render target view to the output merge state of the rendering pipeline (see pipeline states)
6. Set viewport.


The viewport defines the place where you want to render with d3d inside the window. Usually we set the viewport with the same dimentions of the window, but in some cases we want to render in a smaller subrenctangle.

Rendering

Once we have initialized D3D11 we want to render something with D3D11.
For the moment we are going to just clear the backbuffer and present it to the window.


1. Clear Render Target View: We are going to clear all the backbuffer with a specific color using the "ClearRenderTargetView" method in the Context COM.
2. Present: We present the backbuffer using the "Present" method in the SwapChain COM.


Structure

The structure of the program is something like:
WinMain
{
    Initialization (window initialization and d3d initialization)

    main loop (while is running)
    {
        Input( is running ? )
        Render
    }
}


Note:
We haven't created a depth/stencil buffer because we don't need it for a basic D3D application.
But it is required once we begin 3d rendering.

Win32


Create a window: DirectX API doesn't have the functionality to make windows, that's the reason why we need to use an external GUI libreary to handle the window and additionally the user input. In this case we are going to use Win32 API, which is included in almost all windows platforms.

In your Visual C++  go to File -> New -> Project. And then select "Win32 Project". Give it a name, and click "Ok". Click on "Next" and check the "Empty" box.


int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE prevInstance, PSTR pScmdline, int iCmdshow )
{
}

That is the main(){} for windows applications. Each argument from the WinMain is needed for running correctly.

Inside the WinMain we have important things to keep in mind:
1. hInstance (HINSTANCE): An instance for the application, needed for window creation. 
2. WndProc function: It handles the messages for the window (input)
3. wc (WNDCLASSEX): Is the class for the window. It has some settings to be defined. For example, application name, icon, cursor, and so on.
4. hWnd (HWND): It stores the window. The window is created with the function 
CreateWindowEx( arguments... ) 

The functions with Ex at the end are the new Win32 fuctions.
For example CreateWindow( arguments... ) is a depredicated window creation fuction. In modern cases we use CreateWindowEx( arguments... ).