Az előadás letöltése folymat van. Kérjük, várjon

Az előadás letöltése folymat van. Kérjük, várjon

Számítógépes grafika DirectX 2. gyakorlat. Emlékeztető  Előző órán szó volt a COM modellről, amiben az objektumok eljárásait az általuk megvalósított.

Hasonló előadás


Az előadások a következő témára: "Számítógépes grafika DirectX 2. gyakorlat. Emlékeztető  Előző órán szó volt a COM modellről, amiben az objektumok eljárásait az általuk megvalósított."— Előadás másolata:

1 Számítógépes grafika DirectX 2. gyakorlat

2 Emlékeztető  Előző órán szó volt a COM modellről, amiben az objektumok eljárásait az általuk megvalósított felületeken keresztül érhetjük el  WinAPI-ról is volt néhány szó, megismertük mi az a leíró, röviden megnéztük az üzenetfeldolgozást, a WinMain-t stb.  Láttuk, hogy a DirectX több komponensből áll

3 Tartalom  1. DirectX Graphics felépítése  2. Első DirectX-es alkalmazás  3. Képek megjelenítése  4. Szövegkirajzolás

4 DOS-os idők

5 DirectX Graphics felépítése Ezt írjuk mi A programunkban a Direct3D API által biztosított függvényeket hívhatjuk Amiket lefordítja a grafikus kártya driverének „nyelvére” az ún. HAL device

6 DirectX Graphics felépítése  Az alkalmazás és a hardver közötti szoftveres réteg két részből áll:  Direct3D API  HAL

7 Direct3D API  A Direct3D API-t programozzuk az alkalmazásunkból  Ez felületek és függvények halmaza, amiken keresztül elérhetjük az aktuális DX verzió által nyújtott összes szolgáltatást  Azonban ez nem jelenti azt, hogy a hardver is támogatja mindet

8 Hardware Abstraction Layer  A HAL-nak köszönhetően vonatkoztathatunk el a tényleges gépi konfigurációtól  Rajta keresztül történik a kommunikáció a hardverrel  Megtudhatjuk például tőle, hogy milyen szolgáltatásokat valósít meg az aktuális hardver a D3D felületén keresztül elérhetőkből

9 Hardware Abstraction Layer  Ugyanis csak azokat a dolgokat tudja „lefordítani” a videókártya nyelvére ez a réteg, amiket meg is valósítanak az adott hardverben  Mivel közvetlenül használja a hardver nyújtotta szolgáltatásokat (a DDI-n keresztül), ezért a hardver gyártók fejlesztik (amit ki is használnak, ld. 3D Mark botrányok)

10 Mi van a nem megvalósított szolgáltatásokkal?  Úgynevezett pluggable software device- okban minden szoftveresen meg van valósítva  Ilyen például az SDK-val jövő Reference Rasterizer  Ami tehát az aktuális DX verzió összes szolgáltatását megvalósítja  Pontosságra és nem sebességre optimalizált

11 Mi van a nem megvalósított szolgáltatásokkal?  Amikor létrehozzuk a Device-ot (ld. később) megadhatjuk, hogy HAL-on vagy Reference Rasterizer-en keresztül dolgozzon-e  Illetve ha van, egyéb, harmadik fél által gyártott psd-vel

12 A Direct3D grafikus szerelőszalagja A modelleket felépítő transzformálatlan csúcspontok, vertexek A geometriai primitívek (vonal, háromszög stb.), amik a Vertex Data-beli csúcspontok különböző szabályok szerinti összekötésével definiáltak „Csempézés”, magasabbrendű felületek síklapokkal való közelítése. Különböző transzformációk alkalmazása a csúcspontokra (világ, nézet, perspektív, egyéb) Nézeti gúlával vágás, hátrafelé néző lapok eldobása, attríbútum kiértékelések és fragmenteken interpolálása stb. Fragment végső színének kialakítása (textúrázás, megvilágítás stb.) A képernyő adott pixelébe kerülő színének meghatározása (a fragment átmegy kül. teszteken még)

13 Direct3D device  A Direct3D renderelő komponense  Tárolja a működését befolyásoló renderelési állapotokat  Három modulból áll:  Transform module  Lighting module  Rasterizer  Két fő típusa:  HAL device (hardveresen gyorsított)  REF device (referencia eszköz, szoftveres)

14 Direct3D object  Ahhoz, hogy létrehozhassunk egy Direct3D Device- ot (renderelő komponenst), szükségünk van egy Direct3D objektumra (ami nagyjából a fizikai erőforrások összességét képviseli, tőle kérdezhetjük le a hardver képességeit, megjelenítők számát stb.)  Egy-egy Direct3D Device a megjelenítéshez szükséges funkcionálisan teljes részhalmaza lesz a rendelkezésre álló megjelenítéshez szükséges eszközök halmazának  Tehát Device-ban egy konkrét monitor stb.

15 Direct3DDevice  A létrehozandó eszköz megjelenítési tulajdonságait egy D3DPRESENT_PARAMETERS típusú struktúra kitöltésével adhatjuk meg  Itt állíthatjuk be a felbontást és egyebeket

16 Mi jelenik meg a monitoron?  A videókártya memóriájának egyik darabja  A memóriában tárolt képeket DirectX-ben az IDirect3DSurface9 interfészen keresztül érhetjük el

17 Direct3D surface (IDirect3DSurface9)  Egy kép a memóriában (grafikus kártyáéban vagy a rendszerében)  Kitüntetett felületek:  Front Buffer: amikor frissít a monitor, a grafikus kártya a front buffer tartalmát küldi át neki megjelenítésre. Nem írunk rá programból.  Back Buffer: szintén négyszögletes kép, őt írjuk.  Megjelenítéskor ezek váltogatják egymást (double bufferingnél)  Miért nem a Front Buffert írjuk?

18 „Screen Tearing”

19 Swap Chain  Ha frissítés közben változtatnánk a front buffert, akkor a képernyő egy (felső) részén a régebbi kép(rész), az alsón pedig az újabb lenne (tearing)  Ezt többféle módon is el lehet kerülni:  a vertical retrace-t megvárni  back buffering: nem a megjelenített felületre rajzolunk, hanem egy back bufferre, amit majd cserélünk a front bufferrel.  Flipping: a back buffer és a front buffer felcserélése  A swap chain egy vagy több back buffer lánca.

20 Vertical retrace

21 Swap chain példa kettő darab offscreen surface-szel

22 Flipping  A grafikus kártya egyszerűen egy memória hivatkozással tartja számon az aktuális front buffert, ezért egy pointer átállítással megoldható a flip.  Presentation interval: a flipping időbeli módját határozza meg  DEFAULT: megvárja flip előtt a vsync-et  IMMEDIATE: nem várja meg a vsync-et  stb.  Továbbá az is megadható, hogy miként váljon az eddigi front buffer back bufferré (törlődjön a tartalma, maradjanak az adatok stb.)

23 Swap Chain és a D3D Device  A swap chain a Direct3D Device egy belső adattagja  Minden device-nak legalább egy swap chain- je van  Általában minden swap chainhez egy-egy színtérbeli nézetet társítunk  A front buffer azonban nem érhető el, a device belső tulajdonságának tekintjük

24 Tartalom  1. DirectX Graphics felépítése  2. Első DirectX-es alkalmazás  3. Képek megjelenítése  4. Szövegkirajzolás

25 1. példa Ablakos DirectX-es példaprogram

26 Mit is kell tennünk? 1. Létre kell hoznunk egy Direct3D objektumot 2. Majd egy Direct3D Device objektumot 3. Rajzolni valamit a képernyőre az előbbin keresztül 4. Megszüntetni a Direct3D Device objektumot 5. Végül megszüntetni a Direct3D objektumot

27 A program váza Ablak létrehozása Direct3D objektum létrehozása Direct3D Device objektum létrehozása Rajzolás Direct3D objektum megsemmisítése Direct3D Device megsemmisítése Ablak törlése Inicializálás Futás „Takarítás”

28 A program váza InitWindow InitD3DRenderCleanUpD3D CleanUpWindow

29 CDXAppBase elvégzi nekünk A program váza InitWindow InitD3DRenderCleanUpD3D CleanUpWindow

30 CMyDXApp Ezeket az eljárásokat viszont már változtatjuk. A program váza InitWindow InitD3DRenderCleanUpD3D CleanUpWindow

31 A program  Innen indulunk ki: http://people.inf.elte.hu/valasek/bevgraf/02/01 _MyDXApp.zip http://people.inf.elte.hu/valasek/bevgraf/02/01 _MyDXApp.zip  Ez lesz a vége: http://people.inf.elte.hu/valasek/bevgraf/02/01 _MyDXApp_Ready.zip http://people.inf.elte.hu/valasek/bevgraf/02/01 _MyDXApp_Ready.zip

32 CDXApp.h

33 CDXMyApp::CDXMyApp CDXMyApp::CDXMyApp(void) { }

34 CDXMyApp::~CDXMyApp CDXMyApp::~CDXMyApp(void) { }

35 HRESULT CDXMyApp::InitD3D() { m_pD3D = Direct3DCreate9( D3D_SDK_VERSION ); if (!m_pD3D) { return E_FAIL; }... DXAppBase.h-ban: class CDXAppBase {... protected: LPDIRECT3D9 m_pD3D;... };

36 Direct3D objektum létrehozása  A D3D_SDK_VERSION az egyetlen megengedett paramétere a Direct3DCreate9-nak  Sikeres végrehajtás után a visszatérési érték egy mutató lesz a létrehozott objektum IDirect3D9 interfészére  A Direct3D objektum az első amit létrehozunk és az utolsó amit megsemmisítünk

37 Direct3D objektum létrehozása  Rajta keresztül ellenőrizhetjük, hogy milyen képességekkel rendelkezik az aktuális hardver  De csak a létrehozásának pillanatában is már a rendszerhez csatlakoztatott megjelenítőket kezeli  Rajta keresztül hozzuk létre a Direct3D Device objektumot

38 HRESULT CDXMyApp::InitD3D()... ZeroMemory(&m_d3dpp, sizeof(m_d3dpp) ); m_d3dpp.BackBufferWidth= 800; m_d3dpp.BackBufferHeight= 600; m_d3dpp.BackBufferFormat= D3DFMT_UNKNOWN; m_d3dpp.Windowed= TRUE; m_d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;... DXAppBase.h-ban: class CDXAppBase {... protected: D3DPRESENT_PARAMETERS m_d3dpp;... }; void ZeroMemory( PVOID Destination, SIZE_T Length ); Destination: a cím, ahonnan kezdve 0-val töltjük fel a memóriát Length: a 0-val feltöltendő memóriaterület nagysága bájtban

39 Direct3D Device objektum létrehozása  D3DPRESENT_PARAMETERS: A megjelenítés paramétereit adhatjuk meg vele (felbontás, teljes képernyős vagy ablakos alkalmazás-e stb.)  D3DPRESENT_PARAMETERS d3dpp;  Nullázzunk le minden értéket:  ZeroMemory( &d3dpp, sizeof(d3dpp) );

40 D3DPRESENT_PARAMETERS  typedef struct D3DPRESENT_PARAMETERS {… UINT BackBufferWidth, BackBufferHeight;…}  A háttérpuffer (back buffer) felbontása. Teljes képernyős módban ennek az adott videokártyán és monitoron használható különböző megjelenítési módok egyikének szélességével és magasságával kell megegyeznie, ablakosan nem szükséges. Ablakos alkalmazásnál ha 0, akkor az ablak kliensterületének megfelelő érték kerül oda.

41 D3DPRESENT_PARAMETERS  typedef struct D3DPRESENT_PARAMETERS {... D3DSWAPEFFECT SwapEffect;...}  A front buffer back bufferré válásának módja:  D3DSWAPEFFECT_DISCARD: törlődik a tartalma  D3DSWAPEFFECT_FLIP: több back bufferből álló swap chain-nél használják, felcseréli a front buffert a soron következő back bufferrel.  D3DSWAPEFFECT_COPY: csak egy back buffer használata esetén választhatjuk.

42 HRESULT CDXMyApp::InitD3D()... HRESULT hr = m_pD3D->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, m_hWnd, D3DCREATE_HARDWARE_VERTEXPROCESSING, &m_d3dpp, &m_pD3DDevice);...

43 IDirect3D9::CreateDevice  HRESULT CreateDevice( UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags, D3DPRESENT_PARAMETERS * pPresParams, IDirect3DDevice9 ** ppRetDeviceInterface );  Adapter: a használni kívánt megjelenítő eszköz sorszáma, D3DADAPTER_DEFAULT a rendszer elsődleges megjelenítője

44 IDirect3D9::CreateDevice  HRESULT CreateDevice( UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags, D3DPRESENT_PARAMETERS * pPresParams, IDirect3DDevice9 ** ppRetDeviceInterface );  DeviceType: a device típusa, a D3DDEVTYPE enum egy értékét várja (D3DDEVTYPE_HAL, D3DDEVTYPE_REF stb).

45 IDirect3D9::CreateDevice  HRESULT CreateDevice( UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags, D3DPRESENT_PARAMETERS * pPresParams, IDirect3DDevice9 ** ppRetDeviceInterface );  hFocusWindow: annak az ablaknak a leírója, ami figyelmezteti a Direct3D-t, hogy az alkalmazás háttérbe került  Ablakos módban lehet NULL, ha a d3dpp hDeviceWindow adattagjának értéke érvényes.

46 IDirect3D9::CreateDevice  HRESULT CreateDevice( UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags, D3DPRESENT_PARAMETERS * pPresParams, IDirect3DDevice9 ** ppRetDeviceInterface );  BehaviorFlags: egyéb opciók a device létrehozásához (hardveres vagy szoftveres vertexfeldolgozás stb.)

47 IDirect3D9::CreateDevice  HRESULT CreateDevice( UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags, D3DPRESENT_PARAMETERS * pPresParams, IDirect3DDevice9 ** ppRetDeviceInterface );  pPresParams: lásd korábban

48 IDirect3D9::CreateDevice  HRESULT CreateDevice( UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags, D3DPRESENT_PARAMETERS * pPresParams, IDirect3DDevice9 ** ppRetDeviceInterface );  ppRetDeviceInterface: a paraméterben kapott címen lévő mutató a létrehozott Direct3D Device objektum interfészére fog mutatni.

49 HRESULT CDXMyApp::InitD3D()... if( FAILED( hr ) ) { return E_FAIL; } InitDeviceObjects(); return S_OK; }

50 HRESULT CDXMyApp :: InitDeviceObjects()  Ide majd az eszközmemóriába kerülő erőforrások létrehozásának kódja kerül  Egyelőre csak ennyi: HRESULT CDXMyApp:: InitDeviceObjects() { return S_OK; }

51 VOID CDXMyApp :: ReleaseDeviceObjects  Az eszközmemóriába kerülő erőforrások felszabadításának kódja kerül ide  Mivel most nincs ilyen, ez is üres: VOID CDXMyApp:: ReleaseDeviceObjects() { }

52 VOID CDXMyApp :: CleanUpD3D() { if (m_pD3DDevice) { m_pD3DDevice->Release(); m_pD3DDevice = NULL; } if (m_pD3D) { m_pD3D->Release(); m_pD3D = NULL; } }

53 VOID CDXMyApp :: FrameUpdate()  A kirajzolás a Render függvényben fog történni  A FrameUpdate()-ben a kirajzolás logikai részét meghatározó műveleteket végezzük majd el (modellek mozgatása, különböző transzformációk elvégzése stb.)  Egyelőre ez is üres

54 VOID CDXMyApp ::Render() { if (!m_pD3DDevice) return; if( SUCCEEDED(m_pD3DDevice-> BeginScene() ) ) {... Ha a device pointer valamiért NULL, akkor még ne rendereljünk Bejelentjük, hogy rajzolni fogunk, jelezzük az eszköz felé (vagyis az általa reprezentált grafikus megjelenítésben részt vevő hardverek felé), hogy elkezdjük a színtér kirajzolását.

55 VOID CDXMyApp ::Render()... m_pD3DDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0,0,0), 1.0f, 0); }

56 IDirect3DDevice9::Clear  HRESULT Clear( DWORD Count, CONST D3DRECT * pRects, DWORD Flags, D3DCOLOR Color, float Z, DWORD Stencil );  Count: amennyiben több téglalap alakú területen szeretnénk törölni, akkor itt a téglalapok számát kell megadni – ha a pRects!=0, akkor ez sem lehet 0

57 IDirect3DDevice9::Clear  HRESULT Clear( DWORD Count, CONST D3DRECT * pRects, DWORD Flags, D3DCOLOR Color, float Z, DWORD Stencil );  pRects: A törlendő téglalapokat tartalmazó tömbre mutató pointer. Ha NULL, akkor a megjelenítési mező egészét töröljük.

58 IDirect3DDevice9::Clear  HRESULT Clear( DWORD Count, CONST D3DRECT * pRects, DWORD Flags, D3DCOLOR Color, float Z, DWORD Stencil );  Flags: melyik felületet(eket) (surface) töröljük:  D3DCLEAR_TARGET: azt, ahová renderelünk  D3DCLEAR_ZBUFFER  D3DCLEAR_STENCIL  Bináris vagy (|) karakterrel többet is választhatunk

59 IDirect3DDevice9::Clear  HRESULT Clear( DWORD Count, CONST D3DRECT * pRects, DWORD Flags, D3DCOLOR Color, float Z, DWORD Stencil );  Color: ha a renderelési felületet is töröljük, akkor ezzel a színnel fogjuk feltölteni.  D3DCOLOR_* makrók (* lehet XRGB, ARGB stb.)

60 IDirect3DDevice9::Clear  HRESULT Clear( DWORD Count, CONST D3DRECT * pRects, DWORD Flags, D3DCOLOR Color, float Z, DWORD Stencil );  Z: ha a Z-buffert is töröljük, akkor ez az érték kerül bele a korábbiak helyére  A Z-bufferben az értékek 0 és 1 közötti lebegőpontos számok  Az adott pixelben látható pont távolsága

61 IDirect3DDevice9::Clear  HRESULT Clear( DWORD Count, CONST D3DRECT * pRects, DWORD Flags, D3DCOLOR Color, float Z, DWORD Stencil );  Stencil: ha a Stencil buffert is töröljük, akkor pedig ez az érték kerül bele a korábbiak helyére  0-tól 2^n-1 –ig terjedhet az értéke, ahol n a stencil buffer bitmélysége

62 VOID CDXMyApp ::Render()... FrameUpdate(); m_pD3DDevice->EndScene(); } m_pD3DDevice->Present( NULL, NULL, NULL, NULL); }

63

64 Feladat  Változtassuk a kirajzolási színt az idő függvényében!  timeGetTime(): a Windows indulása óta eltelt milliszekundumok számát adja vissza (DWORD-ben)

65 Tartalom  1. DirectX Graphics felépítése  2. Első DirectX-es alkalmazás  3. Képek megjelenítése  4. Szövegkirajzolás

66 Képek megjelenítése  Az előző projektet folytatjuk: 01_MyDXApp_Ready.zip  A kész projekt: 01_DXImages.zip  Az ID3DXSPRITE interfészen keresztül fogjuk a képeket kirajzolni  Szükséges header és lib fájlok (már hozzá vannak adva a projekthez): #pragma comment(lib, "d3dx9.lib") #include

67 Kép kirajzolása  Egy textúrába töltjük be a képfájlt  Majd ezt a textúrát egy sprite-al rajzoljuk ki  A sprite-ot a használt Direct3D Device-hoz hozzuk létre  A sprite és a textúra létrehozásához is már egy létező device kell  Ezért az InitDeviceObjects-be rakjuk ezt a kódot

68 Új adattagok class CDXImageApp : public CDXAppBase {... private: LPD3DXSPRITEm_sprite; LPDIRECT3DTEXTURE9m_texture;... } typedef interface ID3DXSprite *LPD3DXSPRITE; Tehát typedef egy pointerre!

69 HRESULT CDXImageApp:: InitDeviceObjects() { HRESULT hr = D3DXCreateSprite( m_pD3DDevice, &m_sprite); if ( FAILED(hr) ) { return E_FAIL; }...

70 D3DXCreateSprite  HRESULT D3DXCreateSprite( LPDIRECT3DDEVICE9 pDevice, LPD3DXSPRITE * ppSprite );  pDevice: egy érvényes eszközmutató (ő hozza létre a sprite-ot)  ppSprite: egy sprite interfészre mutató pointer címe. Ha sikeres a sprite létrehozása, akkor a függvény az új sprite interfészére állítja ezt a mutatót

71 HRESULT CDXImageApp:: InitDeviceObjects()... hr = D3DXCreateTextureFromFile( m_pD3DDevice, TEXT("hatter.jpg"), &m_texture); if ( FAILED(hr) ) return E_FAIL; return S_OK; }

72 VOID CDXImageApp:: ReleaseDeviceObjects() { if (m_sprite != NULL) { m_sprite->Release(); m_sprite = NULL; } if (m_texture != NULL) { m_texture->Release(); m_texture = NULL; } }

73 VOID CDXImageApp::Render()  Az m_pD3DDevice->BeginScene() hívás utáni részbe írjuk a módosításokat, az UpdateFrame() után közvetlenül  Szükségünk lesz pozíciók megadására  A D3DX utility könyvtárban van egy D3DXVECTOR3 típus  Ez 3 floatból álló tömb, ezt fogjuk használni

74 VOID CDXImageApp::Render()... FrameUpdate(); static D3DXVECTOR3 vCenter(0.0f, 0.0f, 0.0f); static D3DXVECTOR3 vPos(0.0f, 0.0f, 0.0f);...

75 VOID CDXImageApp::Render() m_sprite->Begin(0); m_sprite->Draw( m_texture, NULL, &vCenter, &vPos, D3DCOLOR_XRGB( 255, 255, 255) ); m_sprite->End();...

76 ID3DXSprite::Begin  HRESULT Begin( DWORD Flags );  Flags: a renderelési beállítások módosíthatók itt, például:  D3DXSPRITE_ALPHABLEND: átlátszóságot is kezel

77 ID3DXSprite::Draw  HRESULT Draw( LPDIRECT3DTEXTURE9 pTexture, CONST RECT * pSrcRect, CONST D3DXVECTOR3 * pCenter, CONST D3DXVECTOR3 * pPosition, D3DCOLOR Color );  pTexture: annak a textúrainterfésznek a címe, amibe beletöltöttük a kirajzolni kívánt képet

78 ID3DXSprite::Draw  HRESULT Draw( LPDIRECT3DTEXTURE9 pTexture, CONST RECT * pSrcRect, CONST D3DXVECTOR3 * pCenter, CONST D3DXVECTOR3 * pPosition, D3DCOLOR Color );  pSrcRect: a kép kirajzolni kívánt téglalap alakú tartományát leíró RECT struktúra címe, ha NULL, akkor az egész képet rajzoljuk

79 ID3DXSprite::Draw  HRESULT Draw( LPDIRECT3DTEXTURE9 pTexture, CONST RECT * pSrcRect, CONST D3DXVECTOR3 * pCenter, CONST D3DXVECTOR3 * pPosition, D3DCOLOR Color );  pCenter: mi a sprite középpontja, ha NULL, akkor (0,0,0)-t veszi

80 ID3DXSprite::Draw  HRESULT Draw( LPDIRECT3DTEXTURE9 pTexture, CONST RECT * pSrcRect, CONST D3DXVECTOR3 * pCenter, CONST D3DXVECTOR3 * pPosition, D3DCOLOR Color );  pPosition: a képernyőn hová rajzolja a képet, ha NULL, akkor (0,0,0), ez a képernyő bal- felső sarka

81 ID3DXSprite::Draw  HRESULT Draw( LPDIRECT3DTEXTURE9 pTexture, CONST RECT * pSrcRect, CONST D3DXVECTOR3 * pCenter, CONST D3DXVECTOR3 * pPosition, D3DCOLOR Color );  Color: modulációs szín

82 Feladat  Pattogjon a képernyőn a kép

83 Tartalom  1. DirectX Graphics felépítése  2. Első DirectX-es alkalmazás  3. Képek megjelenítése  4. Szövegkirajzolás

84 Mi kell még  Egy ID3DXFONT interfészre van csak szükségünk  Az előző alkalmazást írjuk tovább  Szükség lesz néhány string-kezelő függvényre is  Ezek a tchar.h-ban lesznek, ezért include-olni kell őt: (DXImageApp.cpp-ben) #include

85 Új adattag class CDXImageApp : public CDXAppBase {... private: ID3DXFont*m_pFont;... }

86 HRESULT CDXImageApp:: InitDeviceObjects() {... hr = D3DXCreateFont( m_pD3DDevice, 24, 0, FW_BOLD, 1, FALSE, DEFAULT_CHARSET, OUT_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_DONTCARE, TEXT("Arial"), &m_pFont );...

87 HRESULT CDXImageApp:: InitDeviceObjects()... if ( FAILED(hr) ) return E_FAIL; return S_OK; }

88 VOID CDXImageApp:: ReleaseDeviceObjects() {... if (m_pFont != NULL) { m_pFont->Release(); m_pFont = NULL; } }

89 VOID CDXImageApp::Render() {… m_pSprite->End(); m_pFont->DrawText( NULL, TEXT(“Hello DirectX!”), -1, NULL, 0, D3DCOLOR_XRGB(255, 255, 255)); … }

90 ID3DXFont::DrawText()  INT DrawText( LPD3DXSPRITE pSprite, LPCTSTR pString, INT Count, LPRECT pRect, DWORD Format, D3DCOLOR Color ); A kirajzolás végző sprite interfészének címe. Ha több szöveget írunk mindenképpen használjuk, lényegesen gyorsabb a szövegmejelenítés így. NULL is érvényes paraméter. A kirajzolandó szöveg. A szöveg hány betűből áll, ha -1 az itt álló érték, akkor megszámolja magától. Mutató egy RECT-re, amibe a kirajzolást végezzük. Szövegformázási tulajdonságok megadása (ide-oda zárás stb.): DT_BOTTOM, DT_CENTER, DT_LEFT, DT_VCENTER,... A kirajzolandó szöveg színe.

91 Szövegkezelés  Előfordulhat, hogy egy változó értékét akarjuk kiírni  Mi most egy formázást használó függvénnyel oldjuk ezt meg:  _stprintf_s  A t a TCHAR-ra utal, a záró s pedig arra, hogy secure, vagyis azt is megadjuk, hogy maximum milyen hosszú bemenetet engedünk meg

92 _stprintf_s  _stprintf_s( TCHAR* _Dst, size_t _SizeInWords, const TCHAR* _FormatString,...)  A _Dst egy mutató annak a memóriaterületnek az elejére, ahonnan kezdve _SizeInWords (Word-ökben adott) hosszan a _FormatString-nek megfelelő szöveg kerül

93 _stprintf_s TCHAR* tSzoveg = new TCHAR[255]; int i = 15; _stprintf_s( tSzoveg, 255, TEXT("A változó értéke: %d"), i);

94 _stprintf_s  A harmadik paraméterben megadott sztringben %d helyett az i változó értéke fog megjelenni  Néhány formázó utasítás:  %d: előjeles egész szám (int)  %f: lebegőpontos szám (double)  %s: string (nullával lezárt)

95 _stprintf_s  A formázó stringbe beírt összes formázó utasításhoz kell átadni értékeket a függvényhíváshoz!  Vagyis a _stprintf_s függvényhívás vége így kell kinézzen:..., ”%d %f %d”, 4, 3.5f, 2);

96 Feladat  Rajzoljuk ki éppen milyen koordinátákon van a pattogó ablakunk


Letölteni ppt "Számítógépes grafika DirectX 2. gyakorlat. Emlékeztető  Előző órán szó volt a COM modellről, amiben az objektumok eljárásait az általuk megvalósított."

Hasonló előadás


Google Hirdetések