MISCELLANEOUS TECHNICAL ARTICLES BY Dr A R COLLINS

Canvas 3D Graphics Library

Cango3D graphics library for HTML canvas

Cango3D provides methods for drawing and animating 3D objects on an 2D HTML canvas. Drawings can be composed of outline paths, filled shapes, stroke text and surfaces. Complex 3D objects can be constructed by maneuvering component objects and adding them to a Group3D to behave as a single entity.

The current version of Cango3D is 14v03, and the source code is available at Cango3D-14v03.js. Full details of the objects, their methods and properties are available in the Cango3D User Guide.

Cango3D basic drawing capability

Here are some examples of drawing and animated using the Cango3D graphics library.

Figure 1. Examples of drawing using the Cango3D graphics library.

Features of Cango3D

  • Simple and lightweight - All Cango3D drawing is based on the primitive object, Path3D which holds the 3D outline path defined using just a few SVG style commands and their 3D coordinate triplets. The Shape3D is a Path3D sub-class. Shape3D paths are always closed and color filled. More complex objects may be grouped as children of a Group3D object. Group3D can also have more Group3Ds as children and so on to form a tree of objects arbitrarily deep.

  • Extension Objects - Extension objects are sub-classes of Group3D but they can have 'preSort' and 'preRender' methods that execute with reference to the Cango3D instance doing the rendering and so can define special behaviours in addition to those inherited from the Group3D or Path3D classes. Several Extension Objects are included in the Cango3D core code. Among these are Panel3D, Text3D, ObjectByExtrusion3D, ObjectByRotation3D etc. Application code can define more Extension Objects as required.

  • World Coordinates - The Cango3D object itself defines the world coordinate system and observer field of view etc. It's 'render' method applies all the user defined transforms to the Pth3D to be drawn, sorts them and maps the 3D coordinates to 2D canvas pixels and calls the native canvas mathods to drawn on the canvas.

  • Shading - When a Shape3D is rendered its fill color is shaded according to the current direction of the user defined light source.

  • Animation - Group3D have a methods translate, rotate, roll, pitch, yaw and scale which apply temporary transforms applied to the object coordinates as they are rendered. The transforms are reset after rendering, new transforms can then be applied at every frame of an animation without changing the underlying definition of the Pathj3D. Children inherit the effect of any transforms applied to the parent group recursively.

  • Drag and Drop - Any object or group can be simply enabled to respond to drag-n-drop or click events by just specifying the callback functions, all the event handling support code is built-in.

Using Cango3D on a web page

Firstly, download the Cango3D JavaScript source file: Cango3D-14v03.js or the minified version Cango3D-14v03-min.js. Copy it to a directory accessible by the web page code. Add the following line to the web page header:

  <script src="source directory/Cango3D-14v03-min.js"></script>

The Cango library file exposes the global objects: Cango3D, Path3D, Shape3D, Group3D and several Extension Objects as globals. Also available are some functions to assist in object construction and manipulation the objects and their descriptors. These are: Cgo3Dsegs, shapeDefs, svgToCgo3D, calcNormal, calcIncAngle.

Within the body of the web page, there must be a canvas element with a unique id.

Typical HTML code is:

 <canvas id="canvasID" width="500" height="300"></canvas>

An instance of a Cango3D graphics context is created as follows:

 const g = new Cango3D(canvasID);

The returned object referenced by g, has the Cango3D methods such as g.setWorldCoords3D, g.clearCanvas, g.setFOV and so on.

Creating an object with Cango3D

A 3D object it is made by first creating its component pieces by calling the constructor of one of the basic objects, Path3D, Shape3D or any of the Extension objects such as Text3D, Panel3D etc. The basic objects take a 'descriptor' argument which defines the outline of the object. The descriptors are strings or arrays of Cgo3D commands and their associated coordinates. These are just commands "M","L","C" and "Z" with x,y,z coordinates and an 'options' argument whose key-value pairs control the appearance of the object.

Text3D take a string as the descriptor whereas Panel3D take 2D SVG path commands as a descriptor without conversion to 3D.

Cango3D provides the shapeDefs global object to simplify defining common shapes. The shapeDefs object has methods to generate circle, ellipse, rectangle, square and triangle all of which take basic dimensions as parameters and return an array of data in 2D SVG format defining the shape outline.

Example

Here is a very simple example, it creates a Panel3D representing a plate using a shapeDefs.circle as its outline path and a Path3D representing a curved stick using a Cgo3D data array defining a cubic Bézier curve. These are then added to a Group3D to move them as one entity. The Group3D's 'rotateY' method is applied with the new rotation angle prior to the Group3D being rendered every 50 msec.

JavaScript source code for this example is shown below:

function drawDemo(cvsID)
{
  const stick = new Path3D(["M",0,0,0, "C", 0,33,0, -5,66,0, -15, 100, 0], 
    {y:-100, strokeColor:"sienna", lineWidth:3});
  const plate = new Panel3D(PathSVG.circle(50), 
    {xRot:-75, fillColor:"yellow", backColor:"green"});
  const plateNstick = new Group3D(stick, plate);
  let angle = 0;

  function turnPlate()
  {
    angle += 20;
    if (angle > 360)
      angle -= 360;

    plateNstick.rotateY(angle);  // apply matrix to Group3D
    g.render(plateNstick);
  }

  const g = new Cango3D(cvsID);
  g.setWorldCoords3D(-75, -120, 150);
  g.setLightSource(0, 500, 200);

  setInterval(turnPlate, 50)        // keep doing this forever
}

Animated sculpture in 3D with draggable base

Here is an example of many of the features of Cango3D working together. The hexagonal display stand base is made by 'objectByRevolution3D' with 6 segments joined by straight lines. The turntable on the display stand has also been made from 'objectByRevolution3D' but with 36 segments joined by arcs. The sculpture is made in the style of Markus Raetz work's. It is made from a single Path3D.

The sculpture is animated using the Timeline utility controlled by the TURN, PAUSE, STEP, STOP control buttons.

The dark green base has been enabled for drag-n-drop so that the display stand can be tilted by clicking and dragging with the mouse. This allows a good view of the ingenuity of the Markus Raetz style sculpture.