
Intro :
Ceci constitue une introduction à la version 10 de DirectX.
DirectX est une interface entre le programmeur et la carte graphique.
Dans cette partie je vais vous apprendre à l’initialiser de manière rudimentaire.
Prérequis :
Savoir programmer en C++.
Première partie :
Création de la fenêtre de rendu.
Explications :
Pensez à configurer les chemins d’accès du SDK de DirectX dans VC++ ! Si vous ne savez pas comment faire : lire ce tutoriel.
On a besoin d’utiliser une fonction qui boucle à chaque fois que l’application reçoit
un message :
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) { case WM_DESTROY: PostQuitMessage(0); break; default: return DefWindowProc(hWnd, message, wParam, lParam); } return 0; } |
Ensuite créez un fichier System.cpp et un fichier System.h où vous mettrez les fonctions que je vous énoncerai.
Voici le fichier System.h :
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 |
#ifndef SYSTEM_H #define SYSTEM_H #include "Defines.h" #include "D3D10Renderer.h" class System { public: System(); virtual ~System(); bool Initialize(); void Shutdown(); bool Frame(); bool Run(); HRESULT SetupTheWindow(); void DestroyTheWindow(); private: // Objet qui gère le rendu de DirectX D3D10Renderer* m_pRenderer; LPCWSTR m_sApplicationName; HINSTANCE m_hInstance; HWND m_Hwnd; bool m_bFullScreen; }; #endif |
Dans le fichier System.cpp. On initialise d’abord une fenêtre Windows ; voici la fonction pour l’initialiser :
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 |
HRESULT System::SetupTheWindow() { // Détermine la résolution de l'écran. unsigned int iScreenWidth = GetSystemMetrics(SM_CXSCREEN); unsigned int iScreenHeight = GetSystemMetrics(SM_CYSCREEN); // Structure de la classe à configurer WNDCLASSEX wcex; // Taille de la structure WNDCLASSEX wcex.cbSize = sizeof( WNDCLASSEX ); // Style de la classe wcex.style = CS_HREDRAW | CS_VREDRAW; // Pointeur de la fonction de boucle de fenêtre (Callback) wcex.lpfnWndProc = WndProc; // Inutile à comprendre wcex.cbClsExtra = 0; // Inutile à comprendre wcex.cbWndExtra = 0; // Obtention de l'instance de cette application wcex.hInstance = m_hInstance; // Icone de la fenêtre wcex.hIcon = LoadIcon(NULL, IDI_WINLOGO); // Icone du pointeur de la souris wcex.hCursor = LoadCursor( NULL, IDC_ARROW ); // Inutile à comprendre wcex.hbrBackground = ( HBRUSH )( COLOR_WINDOW + 1 ); // Inutile à comprendre wcex.lpszMenuName = NULL; // Nom de la classe enregistrée wcex.lpszClassName = m_sApplicationName; wcex.hIconSm = wcex.hIcon; DEVMODE dmScreenSettings; if(m_bFullScreen) { ZeroMemory(&dmScreenSettings, sizeof(dmScreenSettings)); dmScreenSettings.dmSize = sizeof (dmScreenSettings); dmScreenSettings.dmPelsWidth = (unsigned long) iScreenWidth; dmScreenSettings.dmPelsHeight = (unsigned long) iScreenHeight; dmScreenSettings.dmBitsPerPel = 32; dmScreenSettings.dmFields = DM_BITSPERPEL | DM_PELSWIDTH | DM_PELSHEIGHT; ChangeDisplaySettings(&dmScreenSettings, CDS_FULLSCREEN); } if (!RegisterClassEx(&wcex)) return E_FAIL; // Créé la fenêtre RECT rc = { 0, 0, 640, 480 }; AdjustWindowRect( &rc, WS_OVERLAPPEDWINDOW, FALSE ); m_Hwnd = CreateWindow(m_sApplicationName, m_sApplicationName, WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, rc.right - rc.left, rc.bottom - rc.top, NULL, NULL, m_hInstance, NULL); if (!m_Hwnd) return E_FAIL; ShowWindow(m_Hwnd, SW_SHOW); SetForegroundWindow(m_Hwnd); SetFocus(m_Hwnd); return S_OK; } |
Toujours dans System.cpp, la fonction pour détruire la fenêtre :
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
void System::DestroyTheWindow() { // Change les paramètres d'affichage si l'on quitte le mode plein écran if(m_bFullScreen) { ChangeDisplaySettings(NULL, 0); } // Détruit la fenêtre. DestroyWindow(m_Hwnd); m_Hwnd = NULL; // Détruit l'instance de l'application UnregisterClass(m_sApplicationName, m_hInstance); m_hInstance = NULL; } |
La fonction pour initialiser la fenêtre et le Renderer de DirectX 10 :
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
bool System::Initialize() { SetupTheWindow(); m_pRenderer = new D3D10Renderer(m_Hwnd); bool bSucess = m_pRenderer->Initialize(m_bFullScreen); if (!bSucess) { MessageBoxA(NULL, "Erreur d'initialisation de DirectX !", "Erreur", MB_ICONHAND | MB_OK); return false; } return true; } |
La fonction WinMain est dans le fichier Main.cpp et est implémentée de cette façon :
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
#include "D3D10Renderer.h" #include "System.h" int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { System* pSystem = new System(); bool bSucess = pSystem->Initialize(); if (bSucess) { pSystem->Run(); } pSystem->Shutdown(); SAFE_DELETE(pSystem); return 0; } |
Ensuite créez un fichier D3D10Renderer.cpp et un fichier D3D10Renderer.h où vous mettrez les fonctions que je vous énoncerai.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 |
bool D3D10Renderer::Initialize(bool bFullScreen) { HRESULT hr = S_OK;; RECT rc; GetClientRect(m_hWnd, &rc); UINT width = rc.right - rc.left; UINT height = rc.bottom - rc.top; UINT createDeviceFlags = 0; #ifdef _DEBUG createDeviceFlags |= D3D10_CREATE_DEVICE_DEBUG; #endif // Une swap chain représente en fait le back buffer // et le front buffer (principe nommé double buffering) DXGI_SWAP_CHAIN_DESC sd; ZeroMemory(&sd, sizeof(sd)); sd.BufferCount = 1; sd.BufferDesc.Width = width; sd.BufferDesc.Height = height; sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; sd.BufferDesc.RefreshRate.Numerator = 60; sd.BufferDesc.RefreshRate.Denominator = 1; sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; sd.OutputWindow = m_hWnd; sd.SampleDesc.Count = 1; sd.SampleDesc.Quality = 0; sd.Windowed = !bFullScreen; sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; hr = D3D10CreateDeviceAndSwapChain(NULL, D3D10_DRIVER_TYPE_HARDWARE, NULL, createDeviceFlags, D3D10_SDK_VERSION, &sd, &m_pSwapChain, &m_pd3dDevice); if (FAILED(hr)) return false; // Créé le back buffer ID3D10Texture2D* pBackBuffer; hr = m_pSwapChain->GetBuffer(0, __uuidof(ID3D10Texture2D), (LPVOID*)&pBackBuffer); if (FAILED(hr)) return false; // Créé la render target hr = m_pd3dDevice->CreateRenderTargetView(pBackBuffer, NULL, &m_pRenderTargetView); pBackBuffer->Release(); if (FAILED(hr)) return false; m_pd3dDevice->OMSetRenderTargets( 1, &m_pRenderTargetView, NULL ); // Création du viewport D3D10_VIEWPORT vp; vp.Width = width; vp.Height = height; vp.MinDepth = 0.0f; vp.MaxDepth = 1.0f; vp.TopLeftX = 0; vp.TopLeftY = 0; m_pd3dDevice->RSSetViewports( 1, &vp ); return true; } |
La fonction pour afficher le rendu :
|
1 2 3 4 5 6 7 |
void D3D10Renderer::Render() { float afClearColor[4] = {0.0f, 0.125f, 0.3f, 1.0f}; m_pd3dDevice->ClearRenderTargetView(m_pRenderTargetView, afClearColor); m_pSwapChain->Present(1, 0); } |
Résumé :
Nous avons affiché une fenêtre prête à recevoir le rendu de DirectX.
Voici l’archive du code complet pour cette partie : DirectX 10 Tutoriel – Partie 1.zip
Voilà le code et les explications pour initialiser la fenêtre de DirectX 10.
Il reste beaucoup de choses à intégrer pour faire un jeu mais vous saurez au moins comment intégrer DirectX 10.
Références :
– https://takinginitiative.wordpress.com/directx10-tutorials/
– http://www.rastertek.com/tutdx10.html
– DirectX SDK June 2010 Documentation Samples


