Fonction init_D3D

Ici on va initialiser les interfaces Direct3D et Direct3DDevice.
Dans un fichier entête init_D3D.h on définit les pointeurs. une paire pour Direct3D et une paire pour Direct3DDevice puisque l'on aura deux fenêtre à gérer.

#include <d3d9.h>

// pointeurs sur direct3D
static LPDIRECT3D9 obj_Direct3D, obj_Direct3D2;

// pointeurs sur directdevice3D
static LPDIRECT3DDEVICE9 obj_Direct3DDevice, obj_Direct3DDevice2;


dans un fichier decl_init_D3D.h on déclare la fonction


HRESULT InitD3D(HWND, unsigned int, unsigned int, LPDIRECT3D9*, LPDIRECT3DDEVICE9*);

ensuite dans le fichier source init_D3D.cpp on saisi le code suivant :

#include "init_D3D.h"

HRESULT InitD3D(HWND hWnd, unsigned int largeur, unsigned int hauteur, LPDIRECT3D9 *_obj_Direct3D, LPDIRECT3DDEVICE9 *_obj_Direct3DDevice) {

// Création d l'objet Direct3D
if( NULL == ( *_obj_Direct3D = Direct3DCreate9( D3D_SDK_VERSION ) ) )
return E_FAIL;

// récupération du mode d'affichage
D3DDISPLAYMODE d3ddm;
if( FAILED((*_obj_Direct3D)->GetAdapterDisplayMode( D3DADAPTER_DEFAULT, &d3ddm)))
return E_FAIL;

// paramètres

D3DPRESENT_PARAMETERS d3dpp; 
ZeroMemory( &d3dpp, sizeof(d3dpp) );
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferWidth = largeur;
d3dpp.BackBufferHeight = hauteur;
d3dpp.BackBufferFormat = d3ddm.Format;
d3dpp.BackBufferCount = 1;
d3dpp.EnableAutoDepthStencil = TRUE;
d3dpp.AutoDepthStencilFormat = D3DFMT_D16;

// essai en 32 bits

D3DFORMAT formatDePixel = D3DFMT_A8R8G8B8;
d3dpp.BackBufferFormat = formatDePixel;

if( FAILED( (*_obj_Direct3D)->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, _obj_Direct3DDevice ) ) )
{

// essai en 24 bits

D3DFORMAT formatDePixel = D3DFMT_R8G8B8;
d3dpp.BackBufferFormat = formatDePixel;

if( FAILED( (*_obj_Direct3D)->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, _obj_Direct3DDevice ) ) )
{

// essai en 16 bits

D3DFORMAT formatDePixel = D3DFMT_R5G6B5;
d3dpp.BackBufferFormat = formatDePixel;

if( FAILED( (*_obj_Direct3D)->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, _obj_Direct3DDevice ) ) )
{
return E_FAIL;

}

}

}

// paramétré en zbuffer
(*_obj_Direct3DDevice)->SetRenderState( D3DRS_ZENABLE, TRUE );

return S_OK;
}



On commence par créer l'objet Direct3D. L'identificateur D3D_SDK_VERSION permet d'indiquer que la construction se fait à partir du SDK. Ensuite on récupère le mode d'affichage par la méthode GetAdapterDisplayMode et on paramètre le Direct3DDevice, c'est à dire le périphérique Direct3D.

Le paramétrage :

Windowed vaut TRUE pour indiquer qu'on est en mode fenêtre.
SwapEffect vaut D3DSWAPEFFECT_DISCARD pour indiquer qu'il n'y a pas d'effet swap.
Le champ Format sert pour créer un back buffer qui correspond au mode courant de la carte graphique. DirectX applique alors le double buffering qui permet d'éviter les scintillements à l'écran. Le buffer primaire représente l'écran, et le back buffer est utilisé pour préparer et mettre en forme les objets à dessiner.

Ensuite on recherche le meilleur mode graphique : 32 bits, 24 bits puis 16 bits pour la création du périphérique DirectX. Dans le commerce de nos jours les cartes 3D travaillent en 32 bits. La structure d3dpp qui contient les informations sur l'affichage est passée au périphrique, ainsi que le handle hwnd sur la fenêtre de l'application.
Le drapeau D3DCREATE_SOFTWARE_VERTEXPROCESSING indique que ce sera au niveau logiciel que l'on gère les vertex.
La valeur D3DDEVTYPE_HAL demande une gestion graphique au niveau matériel.
A peu de choses près dans les bouquins le code de l'initialisation ressemble à celui-ci à peu de choses près.
Enfin on paramètre le zbuffer, il s'agit d'une méthode de calcul permettant de rendre invisible les faces cachées lors du rendu. Il est calculé par le processeur de la carte graphique.

Dans le code principal on rajoute les lignes :

#include <windows.h>

#include <init_D3D.h>
#include "decl_init_D3D.h"
...

//Création des fenêtres fils
HWND hCtrl_1 = CreateWindow("Joueur_1", "", WS_CHILD|WS_VISIBLE, 0, 0, 300, 300, hWnd, NULL, hInst, NULL);
HWND hCtrl_2 = CreateWindow("Joueur_2", "", WS_CHILD|WS_VISIBLE, 0, 301, 300, 300, hWnd, NULL, hInst, NULL);

// Initialise Direct3D

if(( SUCCEEDED( InitD3D(hCtrl_1, LONG_FENETRE, HAUT_FENETRE, &obj_Direct3D, &obj_Direct3DDevice))
&&
SUCCEEDED( InitD3D(hCtrl_2, LONG_FENETRE, HAUT_FENETRE, &obj_Direct3D2, &obj_Direct3DDevice2))
) == E_FAIL)
return -1;


ShowWindow(hWnd, SW_SHOWDEFAULT);
UpdateWindow(hWnd);

Téléchargez la source, cliquez ci-dessous :