Direct 3D - Zložité objekty
Vytvoriť si nejaký ten trojuholník, štvorec, kocku či valec je pekné, ale pre hru málo. Postavy, predmety to všetko sú zložité objekty. Čudujete sa ako je to možné, že v hrách sa takéto objekty vyskytujú? Možno si myslíte, že programátori hier sú géniovia, keď dokážu vytvoriť objekt z 300 trojuholníkov a ešto ho aj animovať. Našťastie je to oveľa jednoduchšie…
X files
Nie, žiadne Akty X tu nebudú. Direct3D používa tento formát k uloženiu geometrie, materiálov, normálových vektorov a textúr. Všetky zložité objekty vytvoríte v 3D kresliacom programe (3D studio, Truespace, Lightwave…) uložíte (exportujete) ich do formátu napr *.3DS (formát 3D Studia) a pomocou konvertoru od Microsoftu ho skonvertujete na *. X . Potom stačí zopár riadkov kódu a objekt je už v scéne. Nič zložité … to príde až keď sa budete pokúšať animovať. Aj keď to vyzerá sľubne má to jeden háčik. Napríklad si vytvoríte perfektne vyzerajúce auto s množstvom detailov, oblých obrysov. Použijete ho v Direct3D, ale váš počítač nestíha renderovať. Rýchlosť dosahuje okolo 3 Fps, čo nenormálne trhá. Preto nevytvárajte objekty s tisíckami vertexov. Procesor ich nedokáže prepočítavať v reálnom čase. Spustite si nejakú hru a pozorujte. Všímajte si objekty v nej. Zistíte, že sú pomerne hranaté. Väčšinu vizuálnych efektov oblosti tvoria dobre navrhnuté textúry a bump mapping.
Modely
Tak budeme volať zložité objekty. Ak ste už otvorili projekt, určite ste si všimli, že tam nie je žiadna deklarácia vertexu, ani vertex bufferu. I keď je model zložený z vertexov, používa inú premennú - D3DXMESH.
Dim Model As D3DXMesh 'Deklaracia poli pre textury a materialy Dim Model_Material() As D3DMATERIAL8 Dim Model_Textury() As Direct3DTexture8
X súbor môže obsahovať aj niekoľko textúr a materiálov. Tie sa uložia do osobitných polí. U textúr je to trochu zložitejšie. X súbor síce obsahuje informácie o textúrach (kde sa nachádzajú, na ktoré trojuholníky sa majú namapovať, atď.), ale nie textúru samotnú. Tá musí byť uložená osobitne ako bitmapa.
Dim ModelBuffer As D3DXBuffer 'Specialny zasobnik Set Model = D3DX.LoadMeshFromX(App.Path & "\barel.x", D3DXMESH_MANAGED,_ D3DDevice, Nothing, ModelBuffer, Pocet)
Potom model načítame z X súboru do pamäte pomocou funkcie LoadMeshFromX, ktorá zároveň uloží všetky extrahované informácie(materiály, textúry, normálové vektory) do špeciálneho bufferu, ktorým jeD3DXBuffer. Tu vidíte koľko rôznych užitočných funkcií poskytuje pomocná knižnica D3DX.
LoadMeshFromX
filename - cesta a meno X súboru
options = D3DXMESH_MANAGED - nechá na Direct3D, aby vybral spôsob pridelenia pamäte
device = D3dDevice
RetAdjacency = Nothing - nepoužité. Naplní D3DXBuffer s poľom troch Long údajov - špecifikuje 3 susedov každého trojuholníka.
RetMaterials = ModelBuffer - buffer, do ktorého sa uloží pole naplnené údajmi o materiáloch a textúrach. Musí byť typu D3DXBuffer
RetMaterialCount = Pocet - koľko materiálov súbor X obsahuje
Premenná Pocet teraz obsahuje počet materiálov a textúr. Vďaka tomu môžeme predimenzovať polia na presnú veľkosť. Potrebné informácie sú už uložené v špeciálnom dočasnom (temp) zásobníku ModelBuffer. Potom BufferGetMaterial extrahuje materiál z bufferu uloží ho do poľa. Podobne je to aj s textúrami. BufferGetTextureName zistí meno textúry, ktorú následne načíta pomocou CreateTextureFromFileEx.
D3DX.BufferGetMaterial ModelBuffer, I, Model_Material(I) Model_Material(I).Ambient = Model_Material(I).diffuse TextureFile = D3DX.BufferGetTextureName(ModelBuffer, I) Set Model_Textury(I) = D3DX.CreateTextureFromFileEx(D3DDevice,_ App.Path & "\" & TextureFile, 128, 128, D3DX_DEFAULT, 0, D3DFMT_UNKNOWN,_ D3DPOOL_MANAGED,_ D3DX_FILTER_LINEAR, D3DX_FILTER_LINEAR, 0, ByVal 0, ByVal 0)
BufferGetMaterial
materialBuffer = ModelBuffer - buffer obsahujúci materiály
index = I - index materiálu v bufferi
mat = Model_Material(I) - kde sa ziskaný materiál uloží
Knižnica D3DX opäť urobí za vás väčšinu práce. BufferGetMaterial, tak ako aj BufferGetTextureName extrahuje iba jeden materál/textúru s indexom I. Preto ak ich chceme mať všetky, musia byť tieto dva príkazy v cykle. Tak je to aj v zdrojovom kóde.
BufferGetTextureName
materialBuffer = ModelBuffer - D3DXBuffer, ktorý obsahuje materiály
index = I - index textúry
Posledná fáza je renderovanie. Ak model obsahuje viac materiálov a textúr, renderuje sa po častiach (dávkach). Toto zabezpečuje funkcia DrawSubset. Každá časť má svoju textúru a materiál. Takéto “rozkúskovanie” modelu má svoje výhody. Napr. pri animovaní jednotlivých častí. Ale o tom až v ďalších lekciách.
For I = 0 To Pocet - 1 'Nastavenie pouzitia materialu a textur D3DDevice.SetMaterial Model_Material(I) D3DDevice.SetTexture 0, Model_Textury(I) 'Vykresli cast modelu Model.DrawSubset I Next I
Konvertovanie na X súbor
Na vytváranie zložitých objektov je najvhodnejšie použiť 3D Studio Max. Vymodelujete si požadovaný objekt, ktorý dáte uložiť ako 3DS súbor (File/Export). Nahráte ho do adresára, kde sa nachádza aj konvertor (Conv3ds.exe).A začnete konvertovať príkazom:
Conv3DS -m subor.3ds
kde súbor je meno vášho 3DS súboru. Výsledný X súbor má rovnaké meno ako pôvodný 3DS súbor. Parameter -m znamená, že všetky objekty v 3DS súbore budú tvoriť jeden výsledný model a exportuje sa iba jeden frame. Pokiaľ chcete mať v X súbore celú animáciu použite parameter -a. Konvertor si môžete stiahnuť spolu so zdrojovým kódom, ale nachádza sa aj v DX8 SDK dostupný na stránkach Microsoftu (SDK má približne 15 MB).
Skúsenosti s 3D Studiom
Keď exportujete objekt (pomocou parametru -m), ktorý sa skladá z viacerých častí musia byť jeho súčastou (nie samostatne). Inak ich konvertor trocha porozhadzuje. Použite funkciu boolean, aby ste samostatné časti dali dohromady a vytvorili tak “jednoliaty” celok.
Na textúrovanie objektov použite UVW Mapping. Potom bude model v projekte presne tak isto otextúrovaný ako v 3D Studiu.
Počas vytvárania modelu si pozrite z koľkých vertexov a stien sa skladá (menu File/Summanry info). Zvyčajne je počet vertexov v 3D Studiu menší ako v X súbore, kde je stena tvorená trojuholníkom. Na zmenšenie počtu vertexov použite funkciu Optimize. Tá dokáže zmenšiť ich počet aj 5-násobne pri zachovaní rovnakej kvality.
Jedna kompletná 3D scéna by nemala obsahovať viac ako 5000 trojuholníkov. Samozrejme, že to záleží pre aký počítač má byť vás projekt vytvorený. Obzvlášť udržujte jednoduchosť u objektov, ktoré budete chcieť animovať.