Iniziare a utilizzare Three.js

Paul Lewis

Introduzione

Ho utilizzato Three.js per alcuni dei mie esperimenti e fa un ottimo lavoro nell'evitare la seccatura di dover passare il 3D nel browser. Consente di creare videocamere, oggetti, luci, materiali e altro ancora e di scegliere il renderer, il che significa che puoi decidere se vuoi che la scena venga disegnata utilizzando canvas di HTML 5, WebGL o SVG. E poiché è open source, potresti anche partecipare al progetto. Ma ora mi concentrerò su ciò che ho imparato giocandoci come motore e vi illustrerò alcune delle basi.

Per tutta la qualità di Three.js, a volte potresti avere difficoltà. In genere è necessario dedicare molto tempo agli esempi, effettuando il reverse engineering e (nel mio caso, senz'altro) alla ricerca di funzionalità specifiche e di tanto in tanto ponendo domande tramite GitHub. A proposito, ho trovato che Mr. doob e AlteredQualia sono estremamente utili.

1. Nozioni di base

Presumo che tu abbia una conoscenza minima del 3D e una conoscenza ragionevole di JavaScript. Se no, vale la pena imparare un po' prima di provare a giocare con queste cose, poiché possono creare confusione.

Nel nostro mondo 3D avremo alcuni dei seguenti elementi, che ti guiderò nel processo di creazione:

  1. Una scena
  2. Un renderer
  3. Una videocamera
  4. Uno o due oggetti (con materiali)

Puoi, ovviamente, fare delle cose interessanti, e spero che anche tu potrai farlo e iniziare a sperimentare il 3D nel tuo browser.

2. Assistenza

Solo una breve nota sul supporto nei browser. Secondo la mia esperienza, il browser Chrome di Google è il browser migliore con cui lavorare in termini di quali renderer supportati e di velocità del motore JavaScript sottostante. Chrome supporta Canvas, WebGL e SVG ed è incredibilmente veloce. Firefox è il secondo, con l'avvento della versione 4. Il suo motore JavaScript sembra essere un po' più lento di quello di Chrome, ma ancora una volta il supporto per le tecnologie di rendering è ottimo. Opera e Safari stanno aggiungendo il supporto per WebGL, ma le versioni attuali supportano solo canvas. Internet Explorer (versione 9 e successive) supporta solo il rendering della canvas, ma non ho sentito nulla che Microsoft abbia intenzione di aggiungere funzionalità WebGL.

3. Definisci la scena

Immagino che tu abbia scelto un browser che supporta tutte le tecnologie di rendering e che desideri eseguire il rendering con canvas o WebGL, che sono le opzioni più standard. Canvas è più ampiamente supportato rispetto a WebGL, ma vale la pena notare che WebGL viene eseguito sulla GPU della scheda grafica, il che significa che la CPU può concentrarsi su altre attività non di rendering come qualsiasi operazione fisica o interazione dell'utente che stai tentando di fare.

Indipendentemente dal renderer scelto, occorre tenere presente che JavaScript dovrà essere ottimizzato per le prestazioni. Il 3D non è un'attività leggera per un browser (ed è fantastico che sia persino possibile), quindi fai attenzione a capire dove si trovano i colli di bottiglia nel tuo codice e rimuovili se puoi.

Detto questo e supponendo che tu abbia scaricato e incluso tre.js nel tuo file HTML, come procedi con l'impostazione di una scena? come illustrato di seguito:

// set the scene size
var WIDTH = 400,
HEIGHT = 300;

// set some camera attributes
var VIEW_ANGLE = 45,
ASPECT = WIDTH / HEIGHT,
NEAR = 0.1,
FAR = 10000;

// get the DOM element to attach to
// - assume we've got jQuery to hand
var $container = $('#container');

// create a WebGL renderer, camera
// and a scene
var renderer = new THREE.WebGLRenderer();
var camera = new THREE.PerspectiveCamera(
                VIEW_ANGLE,
                ASPECT,
                NEAR,
                FAR );

var scene = new THREE.Scene();

// the camera starts at 0,0,0 so pull it back
camera.position.z = 300;

// start the renderer
renderer.setSize(WIDTH, HEIGHT);

// attach the render-supplied DOM element
$container.append(renderer.domElement);

Non troppo difficile, davvero!

4. Realizzazione di una rete

Abbiamo una scena, una fotocamera e un renderer (ho scelto WebGL nel codice di esempio), ma non abbiamo nulla da disegnare. Three.js in realtà supporta il caricamento di alcuni tipi di file standard diversi, il che è ottimo se esegui l'output di modelli da Blender, Maya, Cinema4D o qualsiasi altra cosa. In altre parole, si tratta di iniziare dopo tutto! Parlerò delle primitive. I primitivi sono maglie geometriche, relativamente basilari come le sfere, i piani, i cubi e i cilindri. Three.js ti consente di creare facilmente questi tipi di primitive:

// set up the sphere vars
var radius = 50, segments = 16, rings = 16;

// create a new mesh with sphere geometry -
// we will cover the sphereMaterial next!
var sphere = new THREE.Mesh(
new THREE.SphereGeometry(radius,
segments,
rings),

sphereMaterial);

// add the sphere to the scene
scene.add(sphere);

Tutto bene, ma che dire del materiale per la sfera? Nel codice è stata utilizzata una variabile sphereMaterial, ma non l'abbiamo ancora definita. Prima dobbiamo parlare dei materiali un po' più in dettaglio.

5. Materiali

Senza dubbio questa è una delle parti più utili di Three.js. Fornisce una serie di materiali comuni (e molto pratici) da applicare alle reti mesh:

  1. "Base", il che significa semplicemente che rende lo stato "spento"
  2. Lambert
  3. Phong

Ce ne sono di più, ma sempre nell'interesse della semplicità vi lascio scoprirle da soli. Nel caso di WebGL, in particolare, questi materiali possono essere salvavita. Perché? Beh, perché in WebGL è necessario scrivere shadower per il rendering di tutto. Gli Shader sono un argomento enorme di per sé, ma in breve sono scritti in GLSL (OpenGL Shader Language), che indica alla GPU come dovrebbe apparire qualcosa. Questo significa che devi imitare i concetti matematici di illuminazione, riflessione e così via. Può diventare molto rapidamente complicato. Grazie a Three.js non dovrai farlo se non vuoi, perché ti permette di estrapolare ciò che ti serve. Tuttavia, se vuoi scrivere shabby, puoi farlo anche con MeshShaderMaterial, per cui la configurazione è flessibile.

Per ora, tuttavia, applichiamo un materiale lambert alla sfera:

// create the sphere's material
var sphereMaterial = new THREE.MeshLambertMaterial(
{
// a gorgeous red.
color: 0xCC0000
});

Vale anche la pena sottolineare che ci sono altre proprietà che puoi specificare quando crei un materiale oltre al colore, come l'arrotondamento o le mappe ambientali. Dovresti visitare la pagina Wiki per scoprire le varie proprietà che puoi impostare sui materiali e, in effetti, qualsiasi oggetto fornito dal motore. Anche threejs.org è nato di recente, offrendo una visione più interessante dell'API.

6. Luci!

Se dovessi eseguire il rendering della scena in questo momento, vedrai un cerchio rosso. Anche se abbiamo applicato un materiale di Lambert, non c'è luce nella scena, quindi per impostazione predefinita Three.js ripristinerà la luce ambientale completa, che equivale a una tonalità piatta. Risolviamo il problema con un semplice punto di luce:

// create a point light
var pointLight = new THREE.PointLight( 0xFFFFFF );

// set its position
pointLight.position.x = 10;
pointLight.position.y = 50;
pointLight.position.z = 130;

// add to the scene
scene.add(pointLight);

7. Rendering

Ora abbiamo davvero tutto pronto per il rendering, incredibilmente. Ma in realtà dobbiamo andare avanti e farlo proprio:

// draw!
renderer.render(scene, camera);

Probabilmente vorrai eseguire il rendering più di una volta, quindi, se intendi creare un loop, dovresti utilizzare requestAnimationFrame; è di gran lunga il modo più intelligente di gestire l'animazione nel browser. Non è ancora completamente supportato, quindi ti consiglio vivamente di dare un'occhiata allo strumento Paul Ireland's shim.

8. Proprietà degli oggetti comuni

Se dedichi del tempo a esaminare il codice di Three.js, vedrai molti oggetti che "ereditano" da Object3D. Questo è un oggetto di base che contiene alcune proprietà molto utili, come le informazioni relative a position, rotation e scale. In particolare, la nostra sfera è una mesh che eredita da Object3D, a cui aggiunge le proprie proprietà: geometria e materiali. Perché li menzioni? È improbabile che tu voglia semplicemente avere una sfera sullo schermo che non fa nulla e vale la pena esaminare queste proprietà perché ti consentono di manipolare all'istante i dettagli sottostanti di mesh e materiali.

// sphere geometry
sphere.geometry

// which contains the vertices and faces
sphere.geometry.vertices // an array
sphere.geometry.faces // also an array

// its position
sphere.position // has x, y and z properties
sphere.rotation // same
sphere.scale // ... same

9. I piccoli segreti

Volevo solo sottolineare un rapido trucco per Three.js: se modifichi, ad esempio, i vertici di un mesh, nel loop di rendering noti che non cambia nulla. Perché? Beh, perché Three.js (per quanto ne ho capito) memorizza nella cache i dati di un mesh come qualcosa di ottimizzazione. Quello che dovete fare è segnalare a Three.js che qualcosa è cambiato in modo che possa ricalcolare tutto. Per eseguire questa operazione, procedi nel seguente modo:

// changes to the vertices
sphere.geometry.__dirtyVertices = true;

// changes to the normals
sphere.geometry.__dirtyNormals = true;

Ce ne sono ancora di più, ma quelle che ho trovato sono le più utili. Ovviamente, dovresti segnalare solo gli elementi che sono cambiati per evitare calcoli inutili.

Conclusione

Spero che questa breve introduzione a Three.js ti sia stata utile. Non c'è niente di meglio che sporcare le mani e provare qualcosa e non c'è niente di meglio di un bel consiglio. L'esecuzione nativa 3D nel browser è molto divertente e l'utilizzo di un motore come Three.js ti consente di rimuovere molti problemi e di creare cose davvero interessanti. Per aiutarti, abbiamo aggregato il codice sorgente in questo articolo del lab, in modo che tu possa utilizzarlo come riferimento. Se ti è piaciuto, fammi sapere su Twitter: è sempre un piacere salutare.