WebGL mit Three.js Grundlagen

3D-Grafiken im Browser sind seit ihrer Einführung ein heißes Thema. Wenn Sie jedoch Ihre Apps mit einfachem WebGL erstellen, dauert dies ewig. Genau aus diesem Grund sind in letzter Zeit einige wirklich nützliche Bibliotheken entstanden. Three.js ist eine der beliebtesten, und ich werde Ihnen in dieser Serie zeigen, wie Sie sie am besten einsetzen können, um Ihren Benutzern ein beeindruckendes 3D-Erlebnis zu bieten.

Bevor wir beginnen, erwarte ich, dass Sie ein grundlegendes Verständnis des 3D-Raums haben, bevor Sie mit dem Lesen dieses Tutorials beginnen, da ich nicht Dinge wie Koordinaten, Vektoren usw. erklären werde.


Schritt 1: Vorbereitung

Erstellen Sie zunächst drei Dateien: index.html, main.js und style.css. Laden Sie jetzt Three.js herunter (vollständige ZIP-Datei mit Beispielen und Quellcode oder nur die JavaScript-Datei nach Ihrer Wahl). Jetzt offen index.html und fügen Sie diesen Code ein:

          

Das ist alles, was Sie in dieser Datei brauchen. Nur eine Deklaration von Skripten und Stylesheet. Alle Magie wird in geschehen main.js, Aber bevor wir dazu kommen, brauchen wir noch einen Trick, damit die App gut aussieht. Öffnen style.css und fügen Sie diesen Code ein:

 Leinwand Position: feststehend; oben: 0; links: 0; 

Dadurch wird die Leinwand in der linken oberen Ecke positioniert, da standardmäßig die Karosserie wird 8px Marge haben. Jetzt können wir mit dem JavaScript-Code fortfahren.


Schritt 2: Die Szene und der Renderer

Three.js verwendet das Konzept einer Anzeigeliste. Dies bedeutet, dass alle Objekte in der Liste gespeichert und dann auf den Bildschirm gezeichnet werden.

Three.js verwendet das Konzept einer Anzeigeliste. Dies bedeutet, dass alle Objekte in der Liste gespeichert und dann auf den Bildschirm gezeichnet werden. Hier ist dies ein Drei Szenen Objekt. Sie müssen der Szene jedes Objekt hinzufügen, das Sie auf dem Bildschirm zeichnen möchten. Sie können beliebig viele Szenen haben, aber ein Renderer kann nur eine Szene gleichzeitig zeichnen (natürlich können Sie die angezeigte Szene wechseln.).

Der Renderer zeichnet einfach alles von der Szene auf die WebGL-Leinwand. Three.js unterstützt auch das Zeichnen in SVG oder 2D Canvas. Wir konzentrieren uns jedoch auf WebGL.

Zunächst können Sie die Breite und Höhe des Fensters in Variablen speichern. Wir werden es später verwenden:

 var width = window.innerWidth; var height = window.innerHeight;

Definieren Sie nun den Renderer und die Szene:

 var renderer = neuer THREE.WebGLRenderer (antialias: true); renderer.setSize (Breite, Höhe); document.body.appendChild (renderer.domElement); var scene = new THREE.Scene;

Die erste Zeile definiert den WebGL-Renderer. Sie können die Optionen des Renderers im ersten Argument als Map übergeben. Hier setzen wir die Antialias true, weil die Kanten der Objekte glatt und nicht gezackt sein sollen.

In der zweiten Zeile wird die Renderergröße auf die Größe des Fensters festgelegt. In der dritten Zeile wird der Renderer hinzugefügt Segeltuch Element des Dokuments (Sie können dies auch mit einer Bibliothek wie jQuery tun: $ ('body'). anfügen (renderer.domElement)).

Die letzte definiert die Szene, es sind keine Argumente erforderlich.


Schritt 3: Der Würfel

Jetzt können Sie etwas hinzufügen, das gezeichnet werden soll. Sei es ein Würfel, da es das einfachste 3D-Objekt ist. In Three.js werden die Objekte, die auf dem Bildschirm gezeichnet werden, als Maschen bezeichnet. Jedes Netz muss eine eigene Geometrie und ein eigenes Material haben. Geometrie ist eine Menge von Punkten, die zum Erstellen des Objekts verbunden werden müssen. Material ist einfach die Farbe (oder die Malerei, aber das ist nicht das Thema dieses Tutorials), die das Objekt abdeckt. Also, lassen Sie uns unseren Würfel erstellen. Zum Glück gibt es in Three.js einige Hilfsfunktionen zum Erstellen von Grundelementen (einfachen Formen):

 var cubeGeometry = new THREE.CubeGeometry (100, 100, 100); var cubeMaterial = new THREE.MeshLambertMaterial (color: 0x1ec876); var cube = new THREE.Mesh (cubeGeometry, cubeMaterial); cube.rotation.y = Math.PI * 45/180; scene.add (Würfel);

Wie Sie sehen, erstellen wir zuerst die Geometrie. Die Argumente definieren eine Größe des Würfels: Breite, Höhe und Tiefe.

Als Nächstes definieren wir das Material des Würfels. In Three.js gibt es einige Materialtypen, aber diesmal verwenden wir die DREI.MeshLambertMaterial, da wir später etwas beleuchten wollen (dieses Material verwendet den Lambert-Algorithmus für Lichtberechnungen). Sie können die Optionen im ersten Argument als Map übergeben, genau wie beim Renderer. Dies ist eine Regel für komplexere Objekte in Three.js. Hier verwenden wir nur Farben, die als Hexadezimalzahl übergeben werden.

In der dritten Zeile erstellen wir ein Netz mit der zuvor erstellten Geometrie und dem verwendeten Material. Als Nächstes drehen wir den Würfel um 45 Grad auf der Y-Achse, damit er besser aussieht. Wir müssen den Grad in Radiant ändern, was mit der Gleichung, die Sie sich wahrscheinlich aus Ihrem Physikunterricht an der Highschool kennen, behandelt wird: Math.PI * 45/180. Schließlich wird der Würfel der Szene hinzugefügt.

Jetzt könntest du öffnen index.html In Ihrem Browser werden die Ergebnisse angezeigt. Sie sehen jedoch nichts, da die Szene noch nicht gerendert wurde.


Schritt 4: Kamera!

Um etwas zu rendern, müssen wir zuerst die Kamera zur Szene hinzufügen, damit der Renderer weiß, aus welcher Sicht er etwas rendern soll. In Three.js gibt es einige Kameratypen, die Sie wahrscheinlich nur verwenden werden THREE.PerspectiveCamera. Diese Art von Kamera zeigt die Szene, wie wir unsere Welt sehen. Lass uns eins erstellen:

 var camera = new THREE.PerspectiveCamera (45, Breite / Höhe, 0,1, 10000);

"Um etwas zu rendern, müssen wir zuerst die Kamera zur Szene hinzufügen, damit der Renderer weiß, aus welcher Sicht er etwas rendern soll."

Das Erstellen der Kamera ist etwas komplizierter als alles andere, was wir bisher gemacht haben. Das erste Argument definiert das FOV (Sichtfeld), den Winkel, von dem aus die Kamera zu sehen ist. Ein FOV von 45 Grad wirkt natürlich. Als Nächstes definieren wir das Verhältnis der Kamera. Dies ist immer die Breite des Renderers geteilt durch seine Höhe, es sei denn, Sie möchten Spezialeffekte erzielen. Die letzten beiden Zahlen legen fest, wie nahe und wie weit das Objekt von der zu zeichnenden Kamera entfernt sein darf.

Jetzt müssen wir die Kamera ein wenig nach oben und hinten bewegen, da die Position aller Objekte, die in Three.js erstellt wurden, in der Mitte der Szene (x: 0, y: 0, z: 0) festgelegt ist:

 camera.position.y = 160; camera.position.z = 400;

Das z Koordinate ist in Richtung des Betrachters positiv, also Objekte mit einem höheren z Position erscheint näher an Ihnen (in diesem Fall erscheinen alle Objekte weiter von Ihnen entfernt, da wir die Kamera bewegt haben).

Jetzt können Sie die Kamera zur Szene hinzufügen und rendern:

 Szene.Add (Kamera); Renderer.Render (Szene, Kamera);

Sie fügen die Kamera so hinzu, wie Sie den Würfel hinzugefügt haben. In der nächsten Zeile wird die Szene mit dieser Kamera dargestellt. Jetzt können Sie den Browser öffnen und Folgendes sollte angezeigt werden:


Sie sollten nur die Oberseite des Würfels sehen können. Das liegt daran, dass wir die Kamera nach oben bewegt haben und sie immer noch ist schauend direkt davor. Sie können dies beheben, indem Sie der Kamera mitteilen, in welcher Position sie sich befinden soll aussehen. Fügen Sie diese Zeile nach den Zeilen hinzu, die die Position der Kamera festlegen:

 camera.lookAt (cube.position);

Das einzige übergebene Argument ist eine Position, an der die Kamera aussehen wird. Nun sieht die Szene besser aus, aber der Würfel ist immer noch schwarz, egal welche Farbe Sie beim Erstellen festgelegt haben:



Schritt 5: Lichter!

Der Würfel ist schwarz, da die Szene nicht beleuchtet ist, also wie ein komplett schwarzer Raum. Sie sehen einen weißen Hintergrund, da sich außerhalb des Würfels nichts zu zeichnen befindet. Um dies zu vermeiden, verwenden wir eine Technik namens Skybox. Grundsätzlich fügen wir einen großen Würfel hinzu, der den Hintergrund der Szene anzeigt (normalerweise weites Gelände, wenn es sich um Freiflächen handelt). So können wir die Box erstellen. Dieser Code sollte vor dem Renderer.Render Anruf:

 var skyboxGeometry = new THREE.CubeGeometry (10000, 10000, 10000); var skyboxMaterial = new THREE.MeshBasicMaterial (color: 0x000000, side: THREE.BackSide); var skybox = new THREE.Mesh (skyboxGeometry, skyboxMaterial); scene.add (Skybox);

Dieser Code ähnelt dem Code, der den Cube erstellt. Diesmal ist die Geometrie jedoch viel größer. Wir haben auch gebraucht THREE.MeshBasicMaterial da wir die skybox nicht anzünden müssen. Beachten Sie auch das zusätzliche Argument, das an das Material übergeben wurde: Seite: DREI.BackSide. Da der Würfel von innen angezeigt wird, müssen wir die gezeichnete Seite ändern (normalerweise zeichnet Three.js nur Außenwände)..

Die gerenderte Szene ist jetzt vollständig schwarz. Um dies zu korrigieren, müssen wir die Szene mit Licht versorgen. Wir werden verwenden THREE.PointLight, die das Licht wie eine Birne aussendet. Fügen Sie diese Zeilen nach der Skybox hinzu:

 var pointLight = new THREE.PointLight (0xffffff); pointLight.position.set (0, 300, 200); scene.add (pointLight);

Wie Sie sehen, haben wir das Punktlicht mit weißer Farbe erstellt. Dann stellen wir die Position ein wenig nach oben und hinten ein, um die Vorderseite und die Oberseite des Würfels zu beleuchten. Schließlich wird das Licht wie jedes andere Objekt zur Szene hinzugefügt. Öffnen Sie den Browser und Sie sollten einen farbigen, schattierten Würfel sehen:


Aber der Würfel ist immer noch ziemlich langweilig. Lassen Sie uns etwas Bewegung hinzufügen.


Schritt 6: Aktion!

Jetzt fügen wir der Szene etwas Bewegung hinzu. Lässt den Würfel um die Y-Achse drehen. Zuerst müssen wir jedoch die Art und Weise ändern, wie wir die Szene rendern. Ein Renderer.Render ruft den aktuellen Status der Szene einmal auf. Selbst wenn wir den Würfel irgendwie animieren, werden wir ihn nicht bewegen sehen. Um dies zu ändern, müssen wir unserer App die Render-Schleife hinzufügen. Dies kann mit dem erreicht werden renderAnimationFrame Funktion, die speziell für diesen Zweck erstellt wurde. Es wird in den meisten gängigen Browsern unterstützt, und für diejenigen, die es nicht unterstützen, hat Three.js eine eigene Polyfill. Also, lass uns das ändern:

 Renderer.Render (Szene, Kamera);

zu diesem:

 function render () renderer.render (Szene, Kamera); requestAnimationFrame (Rendern);  render ();

Tatsächlich gibt es dort keine Schleife, da dies den Browser einfrieren würde. Das requestAnimationFrame Funktion verhält sich ein bisschen wie setTimeout, Es wird jedoch die Funktion aufgerufen, sobald der Browser fertig ist. In der angezeigten Szene hat sich also nichts geändert, und der Würfel bewegt sich immer noch nicht. Lasst uns das beheben. Three.js kommt mit Drei Uhr die verwendet werden kann, um eine reibungslose Animation von Objekten zu erreichen. Initialisieren Sie es vor dem machen Funktionsdefinition:

 var clock = new THREE.Clock;

Nun, bei jedem Anruf clock.getDelta Die Zeit seit dem letzten Anruf wird in Millisekunden zurückgegeben. Dies kann verwendet werden, um den Würfel folgendermaßen zu drehen:

 cube.rotation.y - = clock.getDelta ();

Fügen Sie diese Zeile zwischen den beiden hinzu Renderer.Render und das requestAnimationFrame ruft in die machen Funktion. Es wird einfach die Zeit abgezogen, die von der Drehung des Würfels auf der Y-Achse vergangen ist (denken Sie daran, dass es im Bogenmaß), um den Würfel im Uhrzeigersinn zu drehen. Öffnen Sie nun den Browser und Sie sollten sehen, wie sich Ihr Würfel reibungslos im Uhrzeigersinn dreht.


Fazit

In diesem Teil der Serie haben Sie gelernt, wie Sie die Szene vorbereiten, Objekte und Lichter hinzufügen und Dinge animieren. Sie können mit der App experimentieren, mehr oder verschiedene Objekte hinzufügen, Lichter. Es liegt an dir. Nächstes Mal werde ich Ihnen zeigen, wie Sie Texturen verwenden und wie Sie mit Partikeln schöne Effekte erzeugen. Vergessen Sie nicht, sich die Dokumentation anzusehen, wenn Sie Probleme haben.