Die Präsentation wird geladen. Bitte warten

Die Präsentation wird geladen. Bitte warten

3D-Grafik mit der TriBase-Engine

Ähnliche Präsentationen


Präsentation zum Thema: "3D-Grafik mit der TriBase-Engine"—  Präsentation transkript:

1 3D-Grafik mit der TriBase-Engine
Universität zu Köln Softwaretechnologie II WS 11/12 Dozent: Prof. Dr. M. Thaller Referentin: Nadya Steinert

2 Automatische Initialisierung von Direct3D
Statusänderungen minimieren Texturverwaltung Vertex- und Indexbuffer einfacher erstellen D3DX-Effekte leichter verwalten

3 Die Klasse tbDirect3D Dies ist eine Singleton-Klasse, von der nur eine Instanz erzeugt werden kann Sie verkörpert die vorher benannten Funktionen Die Funktion tbConfigDialog sammelt Informationen über die Direct3D-Einstellungen: Adapter, Videomodi, Oberflächenformate usw. Die Methode tbDirect3D:: Init initialisiert Direct3D und erstellt das Fenster; ihr werden die tbConfig-Struktur und Fenstertitel und -icon übergeben Die Exit- Methode setzt alle Texturen zurück und löscht alle Direct3D-Schnittstellen

4 Klassendeklaration- Variablen
m_bInitialized (BOOL) – am Anfang und nach Herunterfahren FALSE; Variable verhindert mehrfaches Aufrufen der Init-Funktion Zwei Zeiger für die Schnittstellen IDirect3D9 und IDirect3DDevice9 Die D3DCAPS9-Struktur des verwendeten Gerätes speichern Eine HWND-Variable für das Fenster m_bOwnWindow (BOOL) falls der Benutzer eigenes Fenster verwendet Für Kapselung der Methoden SetRenderState, GetRenderState, SetTextureStageState usw. braucht man Tabellen; DWOR- und float-Version Ein Array vom Typ PDIRECT3DBASETEXTURE9 mit 8 Elementen speichert die eingesetzten Texturen m_vScreenSize (tbVector2) speichert die Größe des Bildpuffers in Pixeln

5 Klassendeklaration- Methoden
Init-Methode erwartet zuerst einen Zeiger auf tbConfig , erstellt ein Fenster und initialisiert die IDirect3DDevice9-Schnittstelle; dann ein Fenstername, ein HWND-Parameter für Benutzerfenster, ein HICON-Parameter Kapselungsmethoden für die verschiedenen States die mit den DWORD – und float- Tabellen arbeiten Verschiedene Hilfsmethoden: IsInitialized, GetWindow, GetDirect3D usw. Capture-Methode fragt den aktuellen Status der Geräteschnittstelle ab

6 Die Funktion tbDuConfigDialog
sie ruft den Konfigurationsdialog auf Füllt die tbConfig-Struktur aus, die die gesamte Konfiguration von TriBase-Engine beinhaltet

7 Die Init-Methode Erzeugt das Anwendungsfenster
Eine IDirect3D9-Schnittstelle Ruft CreateDevice auf, um eine IDirect3DDevice9-Schnittstelle zu erhalten Fragt die Gerätefähigkeiten( D3DCAPS9) ab Speichert den aktuellen Status der Tabellen durch die Capture-Methode Setzt Standard-Render und Sampler-States Setzt m_bInitialized auf true

8 Speichern des aktuellen Status mit Capture()
Diese Methode geht alle Render-States, Sampler-States usw. durch, deren Werte in Tabellen gespeichert sind, fragt sie ab und speichert sie Doppelte Statusänderungen werden verhindert indem die Set-Methoden prüfen, ob der Status schon gesetzt ist und wenn dass der Fall ist, wird sofort unterbrochen // Wenn das Render-State schon gesetzt ist, direkt abbrechen if(m_RS.adwRS[RS] == dwValue) return TB_OK;

9 Die Exit-Methode setzt alle Texturen, Index- und Vertex-Buffer zurück, gibt die zwei Schnittstellen frei(D3D und D3DDevice) Methoden wie SetTextue() erhöhen den Zähler der ihr übergebenen Schnittstelle und müssen unbedingt zurückgesetzt werden, damit keine Speicherlecks entstehn Um auf die IDirect3DDevice9 zugreifen zu können, wird der ‚->‘-Operator überladen PDIRECT3DDEVICE9 operetor ->{return m_pD3DDevice;} D3D->DrawPrimitive() //direkt Methoden von IDirect3DDevice9 aufrufen

10 tbTextureManager Sorgt dafür , dass keine Textur zwei Mal geladen wird
Alle geladenen Texturen werden in einer Liste mit deren Dateinamen festgehalten Wenn eine bereits geladene Textur wieder gefragt ist, wird der Referenzzähler der Texturschnittstelle erhöht Wenn der Referenzzähler null erreicht , wird die Textur aus der Liste gelöscht Texturen können aus verschiedenen Quellen geladen werden: aus Speicher, einer Ressource oder aus ZIP_Archiv

11 Klassendefinition von tbTextureManager
Es gibt eine Liste, wo alle Texturen eingetragen werden jeder Textureintrag wird in die Struktur tbTextureListEntry gespeichert struct TRIBASE_API tbTextureListEntry { BOOLbExists;// Existiert diese Textur? PDIRECT3DBASETEXTURE9pTexture;// Die Texturschnittstelle characSourceFilename[256];// Quelldateiname intiWidth;// Breite der Textur intiDepth;// Tiefe der Textur intiHeight;// Höhe der Textur intiNumMIPLevels;// Anzahl der MIP-Mapping-Ebenen D3DFORMATFormat;// Oberflächenformat der Textur DWORDdwUsage;// Verwendungszweck D3DPOOLPool;// Speicherklasse DWORDdwFilter;// Bildfilter (beim Laden) DWORDdwMIPFilter;// MIP-Map-Filter (beim Laden) D3DCOLORColorKey;// Color-Key (beim Laden) };

12 Klassendefinition -Variablen
Für die Texturen wird eine nicht verkette Liste benutzt; der Zeiger m_pTextureList zeigt auf eine tbTextureListEntry-Struktur; Speicher wird dynamischreserviert m_iListSize speichert die aktuelle Größe der Texturliste m_iNumTexture- Anzahl der geladene Texturen

13 Klassendefinition- Methoden
Init-Methode erwartet als Parameter die Ausgangsgröße der Texturliste und reserviert genug Speisher SetListSize verändert die Listengröße, wenn z.B. kein Platz für eine neue Textur da ist GetTextureIndex erwartet als Perameter eine Texturschnitstelle, sucht sie in der Liste und liefert den Texturindex zurück GetNewIndex liefert den nächsten freien Index in der Liste zurück, wenn kein Platz -1; es wird nach dem ersten Listeneintrag gesucht bei dem m_bExist FALSE ist ReleaseTexture erwartet auch eine Texturschnittstelle, sucht die Textur und ruft Release auf; wenn Referenzzähler null, Textur wird gelöscht DeleteAllTexture geht die gesamte Liste durch und ruft für jede Textur so lange Release auf bis Referenzzähler null

14 Klassendefinition -Methoden
AddTextureToList fügt eine Textur zur Liste hinzu, und erweitert diese, wenn kein Platz mehr da ist Load-Methoden für Standard-, Würfel- und Volumentexturen; Für jeden Typ vier verschiedene Versionen, die erwarten Dateiname, Speicheradresse,Ressourcenangabe, oder virtuelle Datei; Die ersten drei Methoden erzeugen eine virtuelle Datei aus der Quelle und rufen die Vierte Version auf; sie haben den gleichen Namen und verschiedene Parameter(immer zuerst die Quellangabe) Get-Methoden bekommen die Parameter einer Textur und durchsuchen die Liste nach einer Übereinstimmung, passende Textur wird zurückgeliefert(Referenzzähler wird erhöht); wenn Textur nicht vorhanden, wird die entsprächende Load-Methode aufgerufen

15 tbVertexBuffer und tbIndexBuffer
Informationen zum Art des Puffers Verwendungszweck: 0 ist Standard; D3DUSAGE_DYNAMIC(dynamischer Puffer);D3DUSAGE_WRITEONLY(kein Lesezugriff; Speicherklasse: die vier Flags D3DPOOL_DEFAULT,D3DPOOL_MANAGED,D3DPOOL_SYSTEMMEM und D3DPOOL_SCRATCHstehen zur Auswahl Sperrmethode: 0, D3DLOCK_NOSYSLOCK, D3DLOCK_DISCARD, D3DLOCK_NOOVERWRITE und D3DLOCK_READONLY

16 Funktionsweise von den Buffern
Beim Initialisieren der Klasse gibt der Benutzer den Verwendungszweck und die Speicherklasse an Die Größe des Index- und Vertex-Buffer kann eventuell angepasst werden Beide Klassen fertigen sich intern eine Kopie des gesamten Puffers an; mit SetVertex und SetIndex kann der Benutzer sie verändern, wenn die Veränderung durchgeführt werden soll, wird Update() aufgerufen Der veränderte Speicherbereich wird gesperrt und die Daten aus der internen Kopie werden in den Puffer kopiert Bei D3DUSAGE_WRITEONLY wird nur aus der Kopie im Systemspeicher gelesen und im Puffer nur geschrieben; GetVertex() fragt Vertizes von der internen Kopie ab

17 Klassendefinition- Variablen(VertexBuffer)
m_pVertexBuffer vom Typ PDIRECT3SVERTEXBUFFER9 m_pBuffer der auf die interne Kopie zeigt, vom Typ void DWORD m_dwSize speichert die Größe des Puffers in Bytes DWORD m_dwVertexSize- die Größe eines einzelnen Vertex DWORD m_dwMaxVertices – Anzahl der Vertizes im Puffer DWORD dwFVF : der Vertexformat, beim Indexbuffer m_IndexFormat (D3DFMT_INDEX16 oder D3DFMT_INDEX32) DWORD m_dwUsage : Verwendungszweck des Puffers, D3DUSAGE_WRIETEONLY ist immer gesetzt D3DPOOL m_Pool: die Speicherklasse, in der sich der Vertex-Buffer befindet

18 Klassendefinition- Variablen(VertexBuffer)
DWORD dwFirstVertex, dwLastVertex speichern die Nummern des ersten und des letzten veränderten Vertex; SetVertex() setzt die Variablen, um später den zu sperrenden Bereich zu ermitteln; nach dem Sperren hat dwFirstVertex den höchst möglichen Wert und dwLastVertex 0 DWORD m_dwCursor speichert die Nummer des nächsten Vertex, der mit AddVertex() gesetzt wird

19 Klassendeklaration- Methoden
Init() generiert die IDirect3DVertexBuffer9-Schnittstelle und die interne Kopie; die erste Version der Methode erwartet die Größe des Vertex-Buffers, die Vertexgröße, den FVF-Bezeichner, Vervwendungszweck und Speicherklasse Die zweite Version erwartet einen bereits existierenden Vertex-Buffer(PDirect3DVertexBuffer9) und die Größe eines Vertex; aus diesem wird die tbVertexBuffer- Instanz initialisiert; GetDesc() fragt die Beschreibung des Vertex-Buffers ab; erste Funktion baut auf die zweite auf Exit() gibt die Schnittstelle und die interne Speicherkopie frei; wird einmal vom Destruktor und einmal am Anfang von Init() aufgerufen SetVertex() erwartet die Nummer des zu setzenden Vertex(0 ist der erste) und den Vertex selbst; der angegebene Vertex wird in die Speicherkopie geschrieben und m_dwFirstVertex und m_dwLastVertex werden aktualisiert

20 Klassendeklaration- Methoden
SetVertices() setzt mehrere Vertizes; erster Parameter: Index des ersten zu setzenden Vertex; dann Anzahl der Vertizes und schließlich Zeiger auf die Vertizes AddVertex() fügte dem Vertex-Buffer einen neuen Vertex hinzu und liefert seinen Index zurück; die Nummer des nächsten Vertex ist im m_dwCursor AddVertices() fügt gleich mehrere Vertizes hinzu, die im zweiten Parameter angegeben sind; Erster Parameter- die Anzahl SetCursor() setzt den Vertexcursor auf den durch den Parameter angegebenen Wert; wenn Vertex-Buffer voll Cursor wird per Hand zurückgesetzt GetVertex() liefert den durch den Index angegebenen Vertex GetVertices() : erste Parameter gibt den Index des ersten abzufragenden Vertex an; 2. Parameter: Anzahl der abzufragenden Vertizes; dritter: Zeiger auf den Speicher Bereich, wo es hinkopiert werden soll

21 Klassendeklaration- Methoden
Update() schreibt die veränderte Vertizes in den Vertex-Buffer; biem dynamischen Puffer Sperflag D3DLOCK_DISCARD; m_dwFirstVertex und m_dwLastVertex werden zurückgesetzt Verschiedene Inline- Methoden

22 tbEffect Optionen zum zeichnen eines Objekts oder eins Materials werden in eine Effekt-Datei gespeichert werden Der Benutzer kann selbst festlegen Welche Techniken benutzt werden oder überlässt das der Klasse Ein globales Effekt-Pool ermöglicht es , das verschiedene Effekte ihre Parameter teilen; wird in Init() erstellt

23 Klassendeklaration- Variablen
LPD3DXEFFECT m_pEffect : die Effekt-Schnittstelle D3DXEFFECT_DESC m_Desc :die Effektbeschreibung BOOL m_bStateSaved: TRUE , wenn beim Aufruf von Begin() angegeben wurde, dass dewr aktuelle Status gespeichert werden soll BOOL m_bCaptureOnFinish: TRUE; WENN BEIM Beenden des Effekts automatisch Capture() aufgerufen werden soll

24 Klassendeklaration - Methoden
5 Init-Methoden: Initialisierung aus einem String , der den gesamten Code enthält; aus einer virtuellen Datei; einer echten Datei, einem Speicherbereich oder einer Ressource Exit() löscht die Schnoittstellen und verringert die Referenzzähler der Texturen SetTechnique: setzt eine Technik , die durch ihre Nummer angegeben wird; gibt man -1 an, sucht die Methode die erste gültige Technik aus Begin() : erster BOOL-Parameter bestimmt, ob die Änderungen später rückgängig gemacht werden sollen; der zweite BOOL-Parametergibt an, ob die internen Tabellen der Render-States, Texturschicht-State usw. in der tbDirect3D-Klasse aktualisiert werden sollen Die beide Parameter werden in m_bStateSaved bzw. in m_bCaptureOnFinish gespeichert;Rückgabewert von Begin() ist die Anzahl der benötigten Durchgänge für den Effekt End() beendet den Effekt Pass() aktiviert den durch seine Nummer angegebenen durchgang

25 Ein Beispiel Die Wasseroberfläche wird in eine Gitter eingeteilt
Die Höhe jedes Vertex wird einmal pro Frame aktualisiert und hängt von der abgelaufene Zeit und von x- un z-position ab Wellen lassen sich durch Sinus-Funktionen simulieren Globale Variablen und Strukturen: zwei Strukturen, eine für die Wasser-Vertizes und eine für die SkyBox-Vertizes // Globale Variablen tbConfigg_Config;// Konfigurationsstruktur PDIRECT3DTEXTURE9g_pWaterTexture = NULL;// Wassertextur PDIRECT3DCUBETEXTURE9g_pEnvMap = NULL;// Umgebungstextur tbEffect*g_pWaterEffect = NULL;// Wassereffekt tbEffect*g_pSkyBoxEffect = NULL;// Sky-Box-Effekt tbVertexBuffer*g_pWaterVB = NULL;// Wasser-Vertex-Buffer tbIndexBuffer*g_pWaterIB = NULL;// Wasser-Index-Buffer tbVertexBuffer*g_pSkyBoxVB = NULL;// Sky-Box-Vertex-Buffer tbIndexBuffer*g_pSkyBoxIB = NULL;// Sky-Box-Index-Buffer const intg_iResolution = 64;// Die Auflösung der Wasseroberfläche floatg_fTime = 0.0f;// Globaler Zeitzähler

26 Programminitialisierung
Konfigurationsdialog wird aufgerufen und das Ergebnis wird in g_Config gespeichert Danach wird die tbDitrect3-Klasse initialisiert Ein Texturemanagerobjekt wird erstellt um die beiden Texturen zu laden InitWater() und InitSkyBox() werden als nächstes aufgerufen Gitterprinzip: es wird ein Statischer IndexBuffer erstellt, der mir den zu dritt gruppierten Indizes gefüllt wird; Die Methode GetVertexIndex(DWORD x, DWORD y) findet den Index jedes Vertex indem sie die Reihe mit der Anzahl Vertizes pro Reihe multipliziert und die Spalte dazu addiert InitWater(): Vertex- und Index-Buffer werden erstellt; IndexBuffer wird gefüllt; Texturen und Effekte werden aufgerufen

27 Die Animation Einmal pro Frame geht das Programm alle Vertizes durch und generiert sie neu, abhängig von position und Zeit; drei Funktionen erwarten eine Positionsangabe und mit hilfe des Zeitzählers liefern die Vertexposition(besonders Höhe), Normalenvektor und Texturkoordinaten: PositionProc(tbVector3 v), NormalProc() und TextureProc() UpdateWater() ruft diese Funktionen auf und füllt den VertexBuffer Die Render-Funktion: der Z-Buffer wird ausgeschaltet

28 Modelldateien Sie sollen flexibel und offen für die Zukunft sein
Flexibilität durch Chunks: jeder Chunk hat ein Header(Beschreibung), gefolgt von den Daten , die Nach Chunktyp interpretiert werden; die Größe der Daten ist im Header angegeben, was erlaubt das unrelevante Chunks einfach übersprungen werden Struktur für ChunkHeader: struct TRIBASE_API tbModelChunkHeader { tbModelChunkTypeChunkType;// Typ des Chunks DWORDdwDataSize;// Größe der Daten des Chunks ChunkType ist vom Typ enum; alle ChunkTypen beginnen mit TB_CT_

29 Vertexdaten-Chunk: TB_CT_MODEL_VERTICES
struct TRIBASE_API tbModelVerticesChunkHeader { DWORDdwFVF;// Vertexformat DWORDdwVertexSize;// Größe eines einzelnen Vertex DWORDdwNumVertices;// Anzahl der Vertizes floatfBoundingSphereRadius;// Radius der umgebenden Kugel tbVector3vBoundingBoxMin;// Minimumpunkt des umgebenden Quaders tbVector3vBoundingBoxMax;// Maximumpunkt des umgebenden Quaders Indexdaten-Chunk TB_CT_MODEL_INDICES struct TRIBASE_API tbModelIndicesChunkHeader D3DFORMATIndexFormat;// D3DFMT_INDEX16 oder D3DFMT_INDEX32 DWORDdwIndexSize;// Größe eines Index DWORDdwNumIndices;// Anzahl der Indizes

30 Effekt-Chunk TB_CT_MODEL_EFFECTS
struct TRIBASE_API tbModelEffectHeader { characName[256];// Name des Effekts BOOLbAlphaBlended;// Mit Alpha-Blending rendern? D3DPRIMITIVETYPEPrimitiveType;// Typ der Primitiven DWORDdwStartIndex;// Wo mit dem Rendern anfangen? DWORDdwNumPrimitives;// Wie viele Primitiven rendern? DWORDdwMinIndex;// Kleinster verwendeter Index DWORDdwNumVertices;// Größter Index - Kleinster Index + 1 DWORDdwEffectCodeSize;// Größe des Effektquellcodes };

31 To be continued…

32


Herunterladen ppt "3D-Grafik mit der TriBase-Engine"

Ähnliche Präsentationen


Google-Anzeigen