{
In dieser Lektion zeige ich Ihnen, wie Sie drei verschiedene Texturfiltermethoden verwenden.
Erfahren Sie, wie Sie mit der Tastatur Objekte in der Szene verschieben und wie Sie einfache Beleuchtung in einer OpenGL-Szene anwenden.
Diese Lektion enthält viele Inhalte. Wenn Sie Fragen zu den vorherigen Lektionen haben, schauen Sie sich diese zunächst noch einmal an.
Bevor Sie sich mit dem Code dahinter befassen, ist es wichtig, die Grundlagen gut zu verstehen.
Wir ändern den Code noch aus der ersten Lektion.
Der Unterschied zu früher besteht darin, dass ich bei jeder großen Änderung den gesamten Code ausschreibe.
Zuerst müssen wir die SysUtils-Unit und die Glaux-Unit hinzufügen.
}
Verwendungsmöglichkeiten
SysUtils,
opengl,
Fenster,
Nachrichten,
Glaux In '../../GLAUX/Glaux.pas';
//Die folgenden Zeilen fügen neue Variablen hinzu.
//Wir fügen drei boolesche Variablen hinzu.
// Die Lichtvariable verfolgt, ob das Licht an ist.
//Variablen lp und fp werden verwendet, um zu speichern, ob die Tasten „L“ und „F“ gedrückt werden.
//Ich werde die Bedeutung dieser Variablen später erklären. Legen Sie das vorerst beiseite.
Licht: Boolean; // Lichtquelle ein/aus
lp : Boolean; // Ist die L-Taste gedrückt?
fp : Boolean; // Ist die F-Taste gedrückt?
//Setzen Sie nun 5 Variablen ein, um die Schrittgröße des Drehwinkels um die x-Achse und die y-Achse zu steuern.
//Und die Rotationsgeschwindigkeit um die x-Achse und die y-Achse.
//Zusätzlich wird eine Z-Variable erstellt, um den Abstand in die Tiefe des Bildschirms zu steuern.
xrot : GLfloat; // X-Rotation
yrot: GLfloat; // Y-Rotation
xspeed : GLfloat; // X-Rotationsgeschwindigkeit
yspeed: GLfloat; // Y-Rotationsgeschwindigkeit
z: GLfloat = -5,0 f; // Abstand tief in den Bildschirm hinein
//Dann legen Sie das Array fest, das zum Erstellen der Lichtquelle verwendet wird.
//Wir werden zwei verschiedene Lichter verwenden.
//Das erste heißt Umgebungslicht. Umgebungslicht kommt aus allen Richtungen.
//Alle Objekte in der Szene werden durch Umgebungslicht beleuchtet.
//Die zweite Art von Lichtquelle wird diffuses Licht genannt.
//Diffuses Licht wird von einer bestimmten Lichtquelle erzeugt und erzeugt Reflexionen auf den Oberflächen von Objekten in Ihrer Szene.
//Jede Objektoberfläche, die direkt mit diffusem Licht beleuchtet wird, wird sehr hell,
//Die kaum beleuchteten Bereiche erscheinen dunkler.
//Dadurch entsteht ein sehr guter Schatteneffekt an den Rändern der von uns erstellten Holzkiste.
//Der Prozess zum Erstellen einer Lichtquelle ist genau der gleiche wie zum Erstellen einer Farbe.
// Die ersten drei Parameter sind die RGB-Dreifarbkomponenten und der letzte ist der Alphakanal-Parameter.
//Deshalb erhalten wir im folgenden Code halbhelles (0,5f) weißes Umgebungslicht.
//Wenn kein Umgebungslicht vorhanden ist, werden Bereiche, die nicht von diffusem Licht getroffen werden, sehr dunkel.
LightAmbient: Array[0..3] Of GLfloat = (0.5, 0.5, 0.5, 1.0); //Umgebungslichtparameter (neu)
//In der nächsten Codezeile erzeugen wir das hellste diffuse Licht.
//Alle Parameterwerte werden auf den Maximalwert von 1,0f gebracht.
//Es wird auf der Vorderseite unserer Holzkiste glänzen und gut aussehen.
LightDiffuse: Array[0..3] Of GLfloat = (1.0, 1.0, 1.0, 1.0); // Diffuse Lichtparameter (neu)
//Zuletzt speichern wir die Position der Lichtquelle.
//Die ersten drei Parameter sind die gleichen wie in glTranslate.
//Die Verschiebungen auf der XYZ-Achse betragen jeweils.
//Da das Licht direkt auf die Vorderseite der Holzkiste scheinen soll, betragen die Verschiebungen auf der XY-Achse beide 0,0.
//Der dritte Wert ist die Verschiebung auf der Z-Achse.
//Um sicherzustellen, dass das Licht immer vor der Holzkiste ist,
//Also bewegen wir die Lichtquelle vom Bildschirm weg zum Betrachter (d. h. zu Ihnen).
// Normalerweise nennen wir die Position des Bildschirms, dh des Bildschirmglases des Monitors, den 0,0-Punkt der Z-Achse.
//Die Verschiebung auf der Z-Achse wird also schließlich auf 2,0 gesetzt.
//Wenn Sie die Lichtquelle sehen können, schwebt sie vor Ihrem Monitor.
//Natürlich kann man die Holzkiste nicht sehen, wenn sie sich nicht hinter dem Bildschirmglas des Monitors befindet.
//『Anmerkung des Übersetzers: Ich schätze NeHes Geduld.
//Um ehrlich zu sein, ärgere ich mich manchmal. Warum redet er so einen Unsinn über so eine einfache Sache?
//Aber wenn alles klar wäre, würden Sie dann immer noch endlos durch solche Seiten blättern? 』
//Der letzte Parameter wird als 1.0f angenommen.
//Dadurch wird OpenGL mitgeteilt, dass die hier angegebenen Koordinaten die Positionen der Lichtquellen sind. Ich werde in zukünftigen Tutorials mehr erklären.
LightPosition: Array[0..3] Of GLfloat = (0.0, 0.0, 2.0, 1.0); // Lichtquellenposition (neu)
//Die Filtervariable verfolgt den bei der Anzeige verwendeten Texturtyp.
//Die erste Textur (Textur 0) wird mit der Filtermethode gl_nearest (nicht glatt) erstellt.
//Die zweite Textur (Textur 1) verwendet die Methode gl_linear (lineare Filterung).
//Das Bild näher am Bildschirm sieht flüssiger aus.
//Die dritte Textur (Textur 2) verwendet die Mipmapped-Filtermethode.
//Dadurch entsteht eine sehr schön aussehende Textur.
//Abhängig von unserem Verwendungstyp ist der Wert der Filtervariablen jeweils gleich 0, 1 oder 2.
//Beginnen wir mit der ersten Textur.
//texture reserviert Speicherplatz für drei verschiedene Texturen.
//Sie befinden sich jeweils in Textur[0], Textur[1] und Textur[2].
filter: GLuint; // Filtertyp
Textur: Array[0..2] Of GLuint; // Speicherplatz für 3 Texturen
PROcedure glGenTextures(n: GLsizei; Var Textures: GLuint);
opengl32;
Prozedur glBindTexture(target: GLenum; texture: GLuint);
opengl32;
Funktion gluBuild2DMipmaps(target: GLenum; Components, width, height: GLint;
Format, atype: GLenum; Daten: Pointer): Integer; externer Glu32-Name
'gluBuild2DMipmaps';
{
Laden Sie nun eine Bitmap und erstellen Sie daraus drei verschiedene Texturen.
In dieser Lektion wird die Glaux-Hilfsbibliothek zum Laden von Bitmaps verwendet.
Daher sollten Sie beim Kompilieren überprüfen, ob die Glaux-Bibliothek enthalten ist.
Ich weiß, dass sowohl Delphi als auch VC++ die Glaux-Bibliothek enthalten, aber andere Sprachen können nicht garantieren, dass sie darüber verfügen.
„Anmerkung des Übersetzers: glaux ist eine OpenGL-Hilfsbibliothek. Gemäß den plattformübergreifenden Eigenschaften von OpenGL,
Der Code sollte auf allen Plattformen gleich sein. Die Hilfsbibliothek ist jedoch nicht die offizielle OpenGL-Standardbibliothek.
Nicht auf allen Plattformen verfügbar. Aber es ist zufällig auf der Win32-Plattform verfügbar.
Haha, BCB ist natürlich auch kein Problem. „Hier kommentiere ich nur den neu hinzugefügten Code.
Wenn Sie Fragen zu einer bestimmten Codezeile haben, schauen Sie sich bitte Tutorial 6 an.
In dieser Lektion wird das Laden und Erstellen von Texturen ausführlich erklärt.
Nach dem vorherigen Codeteil und vor glResizeWnd (),
Wir haben den folgenden Code hinzugefügt. Dies ist fast identisch mit dem Code, der in Lektion 6 zum Laden der Bitmap verwendet wurde.
}
Funktion LoadBmp(filename: pchar): PTAUX_RGBImageRec;
Var
BitmapFile: Thandle; // Dateihandle
Beginnen
Wenn Dateiname = '' Dann // Stellen Sie sicher, dass der Dateiname angegeben ist.
result := Nil; // Wenn nicht angegeben, NULL zurückgeben
BitmapFile := FileOpen(Filename, fmOpenWrite); //Versuchen Sie, die Datei zu öffnen
If BitmapFile > 0 Then // Existiert die Datei?
Beginnen
FileClose(BitmapFile); //Handle schließen
result := auxDIBImageLoadA(filename); //Bitmap laden und Zeiger zurückgeben
Ende
Anders
result := Nil; // Wenn das Laden fehlschlägt, niL zurückgeben.
Ende;
Funktion LoadTexture: boolean; //Bitmap laden und in eine Textur umwandeln
Var
Status: boolean; // Statusanzeige
TextureImage: Array[0..1] Of PTAUX_RGBImageRec; // Texturspeicherplatz erstellen
Beginnen
Status := false;
ZeroMemory(@TextureImage, sizeof(TextureImage)); // Zeiger auf NULL setzen
TextureImage[0] := LoadBMP('Walls.bmp');
Wenn TextureImage[0] <> Null, dann
Beginnen
Status := TRUE; // Status auf TRUE setzen
glGenTextures(1, Texture[0]); // Textur erstellen
//In Lektion 6 haben wir eine linear gefilterte Texturzuordnung verwendet.
//Dies erfordert eine ziemlich hohe Rechenleistung der Maschine, sieht aber ziemlich gut aus.
//In dieser Lektion verwendet die erste Textur, die wir erstellen werden, die GL_NEAREST-Methode.
//Im Prinzip führt diese Methode keine Filterung durch.
//Es beansprucht sehr wenig Rechenleistung und sieht schlecht aus.
//Der einzige Vorteil ist, dass unser Projekt sowohl auf schnellen als auch auf langsamen Maschinen normal laufen kann.
//Sie werden feststellen, dass wir GL_NEAREST sowohl für MIN als auch für MAG verwenden.
//Sie können GL_NEAREST und GL_LINEAR mischen.
//Die Textur wird besser aussehen, aber die Geschwindigkeit ist uns wichtiger, deshalb verwenden wir nur Karten mit geringer Qualität.
//MIN_FILTER wird verwendet, wenn das Bild kleiner als die Originalgröße der Textur gezeichnet wird.
//MAG_FILTER wird verwendet, wenn das Bild größer als die Originalgröße der Textur gezeichnet wird.
// Nächste Filterkarte erstellen
glBindTexture(GL_TEXTURE_2D, Textur[0]);
// Textur erzeugen
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexImage2D(GL_TEXTURE_2D, 0, 3, TextureImage[0].sizeX,
TextureImage[0].sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE,
TextureImage[0].data);
//Die nächste Textur ist dieselbe wie die in Lektion 6, lineare Filterung. Der einzige Unterschied besteht darin, dass es dieses Mal platziert wird
//textur[1]. Denn das ist die zweite Textur. Wenn platziert
//texture[0], es wird die zuvor erstellte GL_NEAREST-Textur überschreiben.
glBindTexture(GL_TEXTURE_2D, textur[1]); //Verwende eine typische Textur, die aus Bitmap-Daten generiert wird
// Textur erzeugen
glTexImage2D(GL_TEXTURE_2D, 0, 3, TextureImage[0].sizeX,
TextureImage[0].sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE,
TextureImage[0].data);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); // Lineare Filterung
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); // Lineare Filterung
//Das Folgende ist eine neue Möglichkeit, Texturen zu erstellen. Mipmapping!
//『Anmerkung des Übersetzers: Ich kann dieses Wort nicht auf Chinesisch übersetzen, aber es spielt keine Rolle. Nachdem Sie diesen Absatz gelesen haben, werden Sie wissen, dass die Bedeutung am wichtigsten ist. 』
// Möglicherweise stellen Sie fest, dass viele Details verloren gehen, wenn das Bild auf dem Bildschirm kleiner wird.
//Das Muster, das gerade gut aussah, ist hässlich geworden. Wenn Sie OpenGL anweisen, eine Mipmap-Textur zu erstellen,
//OpenGL wird versuchen, qualitativ hochwertige Texturen unterschiedlicher Größe zu erstellen. Wenn Sie eine Mipmap-Textur auf den Bildschirm zeichnen,
//OpenGL wählt die am besten aussehende Textur (mit mehr Details), die es erstellt hat, zum Zeichnen aus,
//Anstatt nur das Originalbild zu skalieren (was zu Detailverlust führt).
//Ich habe einmal gesagt, dass es Möglichkeiten gibt, die Einschränkungen zu umgehen, die OpenGL der Texturbreite und -höhe auferlegt – 64, 128, 256 usw.
//Die Lösung ist gluBuild2DMipmaps. Nach meinen Erkenntnissen können Sie beliebige Bitmaps zum Erstellen von Texturen verwenden.
//OpenGL skaliert es automatisch auf normale Größe.
//Da es die dritte Textur ist, speichern wir sie in Textur[2]. Auf diese Weise wurden alle drei Texturen in dieser Lektion erstellt.
//MipMapped-Textur erstellen
glBindTexture(GL_TEXTURE_2D, Textur[2]);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
GL_LINEAR_MIPMAP_NEAREST); // (neu)
//Die folgende Zeile generiert eine Mipmap-Textur.
//Wir verwenden drei Farben (Rot, Grün, Blau), um eine 2D-Textur zu erzeugen.
//TextureImage[0].sizeX ist die Bitmap-Breite,
//TextureImage[0].sizeY ist die Bitmap-Höhe,
//(====Aus irgendeinem Grund verfügt diese Funktion unter Delphi nicht über den Höhenparameter.
//Aber da steht es in der Hilfe. Ich weiß nicht mehr, was Delphi tun wird, was mich deprimiert...
//Schließlich habe ich vorhin selbst ein gluBuild2DMipmaps geschrieben,
//Um die gluBuild2DMipmaps-Funktion in glu32.dll zu laden =====)
//GL_RGB bedeutet, dass wir abwechselnd RGB-Farben verwenden.
//GL_UNSIGNED_BYTE bedeutet, dass die Einheit der Texturdaten Bytes ist.
//TextureImage[0].data zeigt auf die Bitmap, die wir zum Erstellen der Textur verwenden.
gluBuild2DMipmaps(GL_TEXTURE_2D, 3, TextureImage[0].sizeX,
TextureImage[0].sizey, GL_RGB, GL_UNSIGNED_BYTE,
TextureImage[0].data); //(neu) }
Ende;
Wenn zugewiesen(TextureImage[0]) Dann // Ob die Textur existiert
Wenn zugewiesen(TextureImage[0].data) Dann // Ob das Texturbild vorhanden ist
TextureImage[0].data := Nil; // Den vom Texturbild belegten Speicher freigeben
TextureImage[0] := Nil; // Bildstruktur freigeben
Ergebnis := Status; // Rückgabestatus
Ende;
//Dann ist es Zeit, die Textur zu laden und die OpenGL-Einstellungen zu initialisieren.
//Die erste Zeile der GLInit-Funktion verwendet den obigen Code, um die Textur zu laden.
//Nachdem wir die Textur erstellt haben, rufen wir glEnable(GL_TEXTURE_2D) auf, um die 2D-Texturzuordnung zu aktivieren.
//Der Schattenmodus ist auf sanfte Schattierung (sanfte Schattierung) eingestellt.
//Die Hintergrundfarbe wird auf Schwarz gesetzt, wir aktivieren Tiefentests und dann aktivieren wir optimierte Perspektivenberechnungen.
Prozedur glInit(); // Hier alle Einstellungen für OpenGL starten
Beginnen
If (Not LoadTexture) Then // Rufen Sie die Unterroutine zum Laden der Textur auf
exit; // Wenn das Laden fehlschlägt, beenden
glEnable(GL_TEXTURE_2D); // Texturzuordnung aktivieren
glShadeModel(GL_SMOOTH); // Schattenglättung aktivieren
glClearColor(0.0, 0.0, 0.0, 0.0); // schwarzer Hintergrund
glClearDepth(1.0); //Setze den Tiefenpuffer
glEnable(GL_DEPTH_TEST); // Tiefentest aktivieren
glDepthFunc(GL_LESS); // Art des durchgeführten Tiefentests
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); //Hochoptimierte perspektivische Projektionsberechnung
//Jetzt beginnen Sie mit dem Einrichten der Lichtquelle. Die nächste Zeile darunter legt die Menge des emittierten Umgebungslichts fest.
//Lichtquelle Licht1 beginnt Licht auszusenden.
//Zu Beginn dieser Lektion speichern wir die Menge des Umgebungslichts im LightAmbient-Array.
//Jetzt verwenden wir dieses Array (Umgebungslicht mit halber Helligkeit).
glLightfv(GL_LIGHT1, GL_AMBIENT, @LightAmbient[0]); // Umgebungslicht einstellen
//Als nächstes stellen wir die Menge des diffusen Lichts ein. Es wird im LightDiffuse-Array gespeichert (weißes Licht mit voller Helligkeit).
glLightfv(GL_LIGHT1, GL_DIFFUSE, @LightDiffuse[0]); // Diffuses Licht einstellen
//Stellen Sie dann die Position der Lichtquelle ein.
//Die Position wird im LightPosition-Array gespeichert
//(Genau in der Mitte der Vorderseite der Holzkiste, X-0.0, Y-0.0, 2 Einheiten in Z-Richtung zum Betrachter hin bewegt <außerhalb des Bildschirms>).
glLightfv(GL_LIGHT1, GL_POSITION, @LightPosition); // Lichtquellenposition
//Schließlich aktivieren wir Lichtquelle Nummer eins. Wir haben GL_LIGHTING noch nicht aktiviert.
//Du kannst also kein Licht sehen.
//Denken Sie daran: Nur das Einrichten, Positionieren oder auch nur das Aktivieren der Lichtquelle wird nicht funktionieren.
//Es sei denn, wir aktivieren GL_LIGHTING.
glEnable(GL_LIGHT1); // Lichtquelle Nr. 1 aktivieren
Ende;
//Der nächste Codeabschnitt zeichnet den texturierten Würfel. Ich kommentiere nur den neuen Code.
//Wenn Sie Fragen zu Code ohne Anmerkungen haben, gehen Sie zurück zu Lektion 6.
Prozedur glDraw(); // Alle Zeichnungen beginnen hier
Beginnen
glClear(GL_COLOR_BUFFER_BIT Or GL_DEPTH_BUFFER_BIT); // Bildschirm und Tiefenpuffer löschen
glLoadIdentity(); //Setzen Sie die aktuelle Modellbeobachtungsmatrix zurück
//Die nächsten drei Codezeilen platzieren und drehen den Texturwürfel.
//glTranslatef(0.0,0.0,z) verschiebt die Würfel-Z-Einheiten entlang der Z-Achse.
//glRotatef(xrot,1.0f,0.0f,0.0f) dreht den Würfel um die X-Achse xrot.
//glRotatef(yrot,0.0f,1.0f,0.0f) dreht den Würfel yrot um die Y-Achse.
glTranslatef(0.0, 0.0, z); // Verschieben Sie den Bildschirm in Z-Einheiten hinein/aus ihm heraus
glRotatef(xrot, 1.0, 0.0, 0.0); // Um die X-Achse drehen
glRotatef(yrot, 0.0, 1.0, 0.0); // Um die Y-Achse drehen
//Die nächste Zeile ähnelt dem, was wir in Lektion 6 gemacht haben.
// Der Unterschied besteht darin, dass die Textur, die wir binden, diesmal Textur [Filter] ist.
//Anstelle von Textur[0] in der vorherigen Lektion.
//Jedes Mal, wenn wir die F-Taste drücken, erhöht sich der Filterwert.
//Wenn dieser Wert größer als 2 ist, wird der Variablenfilter auf 0 zurückgesetzt.
//Bei der Initialisierung des Programms wird auch der Wert des Variablenfilters auf 0 gesetzt.
//Mit dem Variablenfilter können wir jede der drei Texturen auswählen.
glBindTexture(GL_TEXTURE_2D, texture[filter]); //Wählen Sie die durch den Filter bestimmte Textur aus
glBegin(GL_QUADS); // Beginnen Sie mit dem Zeichnen von Vierecken
//glNormal3f ist neu in dieser Lektion. Normal bedeutet normal.
//Die sogenannte Normale bezeichnet eine Gerade, die durch einen Punkt auf einer Fläche (Polygon) verläuft und senkrecht auf dieser Fläche (Polygon) steht.
//Bei Verwendung einer Lichtquelle muss eine Normale angegeben werden. Die Normale teilt OpenGL die Ausrichtung des Polygons mit und gibt die Vorder- und Rückseite des Polygons an.
//Wenn keine Normalen angegeben werden, können seltsame Dinge passieren: Flächen, die nicht beleuchtet werden sollen, werden beleuchtet, und die Rückseite des Polygons wird ebenfalls beleuchtet....
//Übrigens sollte die Normale zur Außenseite des Polygons zeigen. Wenn Sie auf die Vorderseite der Box schauen, werden Sie feststellen, dass die Normale in die gleiche Richtung wie die positive Z-Achse weist.
//Das bedeutet, dass das Normale auf den Beobachter zeigt – auf dich selbst. Genau das hoffen wir.
//Für die Rückseite der Holzkiste ist, ganz wie wir es wollen, die Normale vom Betrachter abgewandt.
//Wenn der Würfel um 180 Grad entlang der X- oder Y-Achse gedreht wird, ist die Normale auf der Vorderseite immer noch dem Betrachter zugewandt und die Normale auf der Rückseite ist immer noch vom Betrachter weg gerichtet.
//Mit anderen Worten, egal um welche Oberfläche es sich handelt, solange sie dem Beobachter zugewandt ist, zeigt die Normale dieser Oberfläche auf den Beobachter.
//Da sich die Lichtquelle unmittelbar neben dem Beobachter befindet, wird diese Oberfläche immer dann beleuchtet, wenn die Normale dem Beobachter zugewandt ist.
//Und je näher das Normal an der Lichtquelle liegt, desto heller erscheint es.
//Wenn Sie den Beobachtungspunkt innerhalb des Würfels platzieren, erhalten Sie Dunkelheit innerhalb der Normalen.
//Weil die Normale nach außen zeigt. Befindet sich im Inneren des Würfels keine Lichtquelle, ist es natürlich stockfinster.
// Vorne
glNormal3f(0.0, 0.0, 1.0); // Normal zeigt auf den Beobachter
glTexCoord2f(0.0, 0.0);
glVertex3f(-1.0, -1.0, 1.0); // Textur und unten links im Quad
glTexCoord2f(1.0, 0.0);
glVertex3f(1.0, -1.0, 1.0); // Textur und unten rechts im Quad
glTexCoord2f(1.0, 1.0);
glVertex3f(1.0, 1.0, 1.0); //Textur und oben rechts im Quad
glTexCoord2f(0.0, 1.0);
glVertex3f(-1.0, 1.0, 1.0); //Textur und oben links im Quad
// später
glNormal3f(0.0, 0.0, -1.0); // Normal zeigt vom Betrachter weg
glTexCoord2f(1.0, 0.0);
glVertex3f(-1.0, -1.0, -1.0); // Textur und unten rechts im Quad
glTexCoord2f(1.0, 1.0);
glVertex3f(-1.0, 1.0, -1.0); //Textur und oben rechts im Quad
glTexCoord2f(0.0, 1.0);
glVertex3f(1.0, 1.0, -1.0); //Textur und oben links im Quad
glTexCoord2f(0.0, 0.0);
glVertex3f(1.0, -1.0, -1.0); // Textur und unten links vom Quad
// Oberseite
glNormal3f(0.0, 1.0, 0.0); // normal nach oben
glTexCoord2f(0.0, 1.0);
glVertex3f(-1.0, 1.0, -1.0); //Textur und oben links im Quad
glTexCoord2f(0.0, 0.0);
glVertex3f(-1.0, 1.0, 1.0); // Textur und unten links im Quad
glTexCoord2f(1.0, 0.0);
glVertex3f(1.0, 1.0, 1.0); // Textur und unten rechts im Quad
glTexCoord2f(1.0, 1.0);
glVertex3f(1.0, 1.0, -1.0); //Textur und oben rechts im Quad
// Unten
glNormal3f(0.0, -1.0, 0.0); // normal nach unten zeigend
glTexCoord2f(1.0, 1.0);
glVertex3f(-1.0, -1.0, -1.0); // Textur und oben rechts im Quad
glTexCoord2f(0.0, 1.0);
glVertex3f(1.0, -1.0, -1.0); //Textur und oben links im Quad
glTexCoord2f(0.0, 0.0);
glVertex3f(1.0, -1.0, 1.0); // Textur und unten links im Quad
glTexCoord2f(1.0, 0.0);
glVertex3f(-1.0, -1.0, 1.0); // Textur und unten rechts im Quad
// Rechts
glNormal3f(1.0, 0.0, 0.0); // normal nach rechts
glTexCoord2f(1.0, 0.0);
glVertex3f(1.0, -1.0, -1.0); // Textur und unten rechts im Quad
glTexCoord2f(1.0, 1.0);
glVertex3f(1.0, 1.0, -1.0); //Textur und oben rechts im Quad
glTexCoord2f(0.0, 1.0);
glVertex3f(1.0, 1.0, 1.0); //Textur und oben links im Quad
glTexCoord2f(0.0, 0.0);
glVertex3f(1.0, -1.0, 1.0); // Textur und unten links vom Quad
// links
glNormal3f(-1.0, 0.0, 0.0); // normal nach links
glTexCoord2f(0.0, 0.0);
glVertex3f(-1.0, -1.0, -1.0); // Textur und unten links vom Quad
glTexCoord2f(1.0, 0.0);
glVertex3f(-1.0, -1.0, 1.0); // Textur und unten rechts im Quad
glTexCoord2f(1.0, 1.0);
glVertex3f(-1.0, 1.0, 1.0); //Textur und oben rechts im Quad
glTexCoord2f(0.0, 1.0);
glVertex3f(-1.0, 1.0, -1.0); //Textur und oben links im Quad
glEnd();
xrot := xrot + xspeed; // xrot erhöht xspeed-Einheiten
yrot := Yrot + yspeed; // yrot erhöht yspeed-Einheiten
Ende;
//Gehen Sie nun zur Hauptfunktion WinMain().
//Wir werden hier Steuercode hinzufügen, um die Lichtquelle ein- und auszuschalten, die Holzkiste zu drehen, Filtermethoden zu wechseln und die Holzkiste näher und weiter weg zu bewegen.
// Gegen Ende der WinMain()-Funktion sehen Sie die Codezeile SwapBuffers(hDC).
//Dann fügen Sie nach dieser Zeile den folgenden Code hinzu.
//Der Code prüft, ob die L-Taste gedrückt wurde.
// Wenn die L-Taste gedrückt wurde, der Wert von lp jedoch nicht falsch ist, bedeutet dies, dass die L-Taste nicht losgelassen wurde und zu diesem Zeitpunkt nichts passiert.
SwapBuffers(h_DC); // Swap-Puffer (Doppelpuffer)
If (keys[ord('L')] And Not lp) Then
Beginnen
//Wenn der Wert von lp falsch ist,
//Bedeutet, dass die L-Taste noch nicht gedrückt oder losgelassen wurde, dann wird lp auf TRUE gesetzt.
// Der Grund für die gleichzeitige Überprüfung dieser beiden Bedingungen besteht darin, zu verhindern, dass die L-Taste gedrückt wird.
//Dieser Code wird wiederholt ausgeführt und führt dazu, dass das Formular kontinuierlich blinkt.
//Nachdem lp auf true gesetzt ist, erkennt der Computer, dass die L-Taste gedrückt wurde.
//Wir können die Lichtquelle entsprechend ein-/ausschalten: Die boolesche Variable Licht steuert das Ein-/Ausschalten der Lichtquelle.
lp := true; // lp ist auf TRUE gesetzt
Licht := Nicht Licht; // Lichtquelle auf TRUE/FALSE schalten
Wenn kein Licht, dann // Wenn keine Lichtquelle vorhanden ist
glDisable(GL_LIGHTING) //Lichtquelle deaktivieren
Sonst // Andere
glEnable(GL_LIGHTING); //Lichtquelle aktivieren
Ende;
Wenn nicht, Tasten[ord('L')], dann //Wird die L-Taste losgelassen?
lp := FALSE; // Wenn ja, setze lp auf FALSE
//Führen Sie dann eine ähnliche Prüfung für die Taste „F“ durch.
//Wenn die Taste „F“ gedrückt wird und die Taste „F“ nicht gedrückt wird oder noch nie gedrückt wurde,
//Variable fp auf true setzen. Dies bedeutet, dass die Taste gedrückt wird.
//Dann fügen Sie eins zur Filtervariablen hinzu. Wenn die Filtervariable größer als 2 ist
//(Da das Array, das wir hier verwenden, Textur[3] ist, existieren keine Texturen größer als 2),
//Wir setzen die Filtervariable auf 0 zurück.
If (keys[ord('F')] And Not fp) Then // Ist die F-Taste gedrückt?
Beginnen
fp := TRUE; // fp ist auf TRUE gesetzt
inc(filter); // Addiere eins zum Wert von filter
Wenn Filter > 2, dann // Ist er größer als 2?
filter := 0; // Wenn auf 0 zurückgesetzt
Ende;
If Not keys[ord('F')] Then //Wurde die F-Taste losgelassen?
fp := FALSE; // Wenn fp auf FALSE gesetzt ist
//Diese vier Zeilen prüfen, ob die PageUp-Taste gedrückt ist. Wenn ja, verringern Sie den Wert der z-Variablen. Auf diese Weise bewegt der in der DrawGLScene-Funktion enthaltene Aufruf von glTranslatef(0.0f,0.0f,z) die Holzkiste weiter vom Betrachter weg.
Wenn die Tasten [VK_PRIOR] dann //PageUp gedrückt werden?
z := z - 0,02; // Wenn gedrückt, bewegen Sie die Holzkiste in Richtung der Innenseite des Bildschirms.
//Die nächsten vier Zeilen prüfen, ob die PageDown-Taste gedrückt wird. Wenn ja, erhöhen Sie den Wert der z-Variablen. Auf diese Weise bewegt der in der DrawGLScene-Funktion enthaltene Aufruf glTranslatef(0.0f,0.0f,z) die Holzkiste näher an den Betrachter heran.
Ifkeys[VK_NEXT] Then // Wird PageDown gedrückt?
z := z + 0.02; //Wenn gedrückt, bewegen Sie die Holzkiste in Richtung des Betrachters.
//Jetzt die Pfeiltasten prüfen. Drücken Sie die linke und rechte Richtungstaste, um die Geschwindigkeit entsprechend zu verringern oder zu erhöhen.
//Drücken Sie die Auf- und Ab-Richtungstasten, um die Geschwindigkeit entsprechend zu verringern oder zu erhöhen.
// Denken Sie daran, dass sich der Würfel in zukünftigen Tutorials schneller dreht, wenn die Werte von xspeed und yspeed erhöht werden.
//Wenn Sie eine bestimmte Richtungstaste gedrückt halten, dreht sich der Würfel schneller in diese Richtung.
Wenn Tasten[VK_UP] Dann // Wird die Aufwärts-Richtungstaste gedrückt?
xspeed := xspeed - 0.01; //Wenn ja, xspeed reduzieren
Wenn Tasten[VK_DOWN] Dann //Wurde die Abwärts-Richtungstaste gedrückt?
xspeed := xspeed + 0.01; //Wenn ja, xspeed erhöhen
Wenn Tasten[VK_RIGHT] Dann //Wird die rechte Richtungstaste gedrückt?
yspeed := yspeed + 0,01; //Wenn ja, yspeed erhöhen
Wenn Tasten[VK_LEFT] Dann //Wird die linke Richtungstaste gedrückt?
yspeed := yspeed - 0,01; //Wenn ja, yspeed reduzieren
If (keys[VK_ESCAPE]) Then // Wenn die ESC-Taste gedrückt wird
fertig := Stimmt
Führen Sie es aus und sehen Sie den Effekt