Page 3: Comparing 3D APIs
Spring 2026 Sample Solution
On this page, we’ll return to our spinning cube example to see the graphics concepts that we need to make it. We’ll look at how we can implement these concepts in various APIs (we’ll focus on three.js).
The key lesson I want to convey is that the core concepts of 3D graphics lead directly to abstractions (or objects) in the high-level API.
The Cube, Again…
Here is the spinning cube again (we’ll keep coming back to it). But, rather than showing you my version (from the first page), I asked an AI (Gemini) to rewrite it using the four different APIs…
If you want to see the actual programs, they are:
- HTML5 Canvas: cube_canvas2d.js
- Three.JS: cube_threejs.js
- WebGL: cube_webgl.js
- WebGPU: cube_webgpu.js
Notice how the three.js version is much shorter. This is because three.js builds in a lot of the things we need to do 3D graphics.
| File | Total Lines | Code Lines (No comments/blanks) |
|---|---|---|
cube_threejs.js |
45 | 26 |
cube_canvas2d.js |
118 | 81 |
cube_webgl.js |
163 | 113 |
cube_webgpu.js |
236 | 188 |
The code counts are actually even worse: all the libraries (other than three.js) require a separate matrix library. Since three.js is designed to do graphics, and you can’t do 3D graphics without matrices, it has a matrix library built in.
How do you do this in Canvas?
We can think of all the things that we would need to do to make the spinning cube in Canvas. This can help us appreciate what three.js does for us.
This refers to the code in cube_canvas2d.js .
- We need to define the cube. The cube is made of triangles, so we need a list of the polygons (their vertices and how they connect). (lines 14-27). Three has cubes built in, but more generally, it has good data structures for representing collections of triangles. That said, in three (like most 3D APIs), we need to break things into triangles.
- We need to position the cube in the scene (world). This takes care of the rotation for spinning. Because there is just one object, and it has a simple transformation, we can just have the world be “implicit” (no data structure to represent it), and have a single matrix to transform the one object. You can see the transformation on lines 53-57.
- We need the “camera” to transform points in the scene to positions on the screen. The program uses the matrix library to create the appropriate perspective matrix. (lines 48-51). In three, we abstract this as the camera.
- The drawing process needs to transform all of the points. (lines 63-67) Three takes care of this for us.
- For each polygon, we need to compute what direction it is facing (its “normal”) so that we can determine how much light it receives. (lines 71-84) Again, three takes care of this for us.
- For each polygon, we need to compute how much light hits it and determine its color accordingly. (lines 87-92) Three does this computation as part of its lighting system.
- To make sure the closer polygons cover the farther ones, the Canvas program uses something called the “Painter’s Algorithm.” Basically, it takes the polygons and sorts them based on how far they are. (line 98). Three handles occlusions for us using a different algorithm that uses the graphics hardware.
- The program draws the polygons in the sorted order, making sure to apply the different transformations correctly. (lines 101-114). Three takes care of drawing all the objects for us, using the graphics hardware. Because of the way the graphics hardware handles occlusions, the order of the polygons doesn’t matter.
Basically, the Canvas program has to implement all of the 3D graphics concepts. Three encapsulates them nicely.
Why is the WebGL (or WebGPU) program so long?
If you look at the WebGL version cube_webgl.js or the WebGPU version cube_webgpu.js , you will notice that (1) they are very long, (2) they include programs in other languages (that run directly on the hardware), and (3) the abstractions are more hardware-oriented (buffers, compilers) than graphics-oriented.
You might think that since WebGL (or WebGPU) is meant for doing 3D graphics, it would make it easy to do basic 3D graphics. But a better way to think of these APIs is that they are not 3D graphics APIs: they are APIs to access the hardware. You still need to write all the graphics programming yourself (and map it to the hardware).
If you look at the WebGL program, you will see that all the calculations are explicitly programmed. The lighting computations need to be written (in GLSL). The transformations need to be written (at least the program uses the matrix library rather than writing the rotation and perspective matrices). The shape data (the set of triangles) needs to be put in special memory blocks that can be transferred to the graphics hardware. The layout of the data in memory needs to be described to the graphics hardware. And so on.
Because we want to focus on the graphics concepts, we’ll use a high-level API to take care of these details. In a later workbook, we’ll study how the graphics hardware works, so we can learn how to program it. But even then, we will use the high-level API so we can do the parts of hardware programming that are interesting.
Next: Page 4 - Some 3D Math