How To

Create Parametric Shapes - Legacy


How To Create Parametric Shapes using Legacy Method

Ribbon

For details on what it is and how it is constructed you might want to read the Ribbon Tutorial

var ribbon = BABYLON.Mesh.CreateRibbon("ribbon", [path1, path2, ..., pathn], false, false, 0, scene, false, BABYLON.Mesh.DEFAULTSIDE);

Parameters are: name, pathArray, closeArray, closePath, offset, scene, updatable? (if the mesh must be modified later) and the optional side orientation (see below).

  • name : a string, the name you want to give to your shape,
  • pathArray : an array populated with paths. Paths are also arrays, populated with series of successive Vector3. You need at least one path to construct a ribbon and each path must contain at least four Vector3,
  • closeArray : boolean, if true an extra set of triangles is constructed between the last path and the first path of pathArray,
  • closePath : boolean, if true the last point of each path of pathArray is joined to the first point of this path,
  • offset : integer (default half the path size) mandatory only if the pathArray contents only one path. The ribbon will be constructed joining each i-th point of the single path to the i+offset-th point. It is ignored if pathArray has more than one path,
  • scene : the current scene object,
  • updatable : boolean, if the ribbon should allow updating later,
  • sideOrientation : the wanted side-orientation (BABYLON.Mesh.FRONTSIDE / BACKSIDE / DOUBLESIDE / DEFAULT).

The last two parameters can be omitted if you just need the default behavior :

var ribbon = BABYLON.Mesh.CreateRibbon("ribbon", [path1, path2, ..., pathn], false, false, 0, scene);

Tube

var tube = BABYLON.Mesh.CreateTube("tube", [V1, V2, ..., Vn], radius, tesselation, radiusFunction, cap, scene, false, BABYLON.Mesh.DEFAULTSIDE);

Parameters are : name, path, radius, tesselation, optional radiusFunction, cap, scene, updatable, sideOrientation.

  • name : string, the name of the tube mesh,
  • path : an array of successive Vector3, at least two Vector3,
  • radius : nuumber, the tube radius, used when radiusFunction parameter set to null,
  • tesselation : the number of radial segments,
  • radiusFunction : optional, a javascript function returns a radius value. This can be set to null,
  • cap : BABYLON.Mesh.NO_CAP, BABYLON.Mesh.CAP_START, BABYLON.Mesh.CAP_END, BABYLON.Mesh.CAP_ALL,
  • updatable : boolean, if the tube should allow updating later,
  • sideOrientation : the wanted side orientation (front, back or double side).

The last two parameters can be omitted if you just need the default behavior :

var tube = BABYLON.Mesh.CreateTube("tube", [V1, V2, ..., Vn], radius, tesselation, radiusFunction, cap, scene);

While a tube can just be a cyclinder it can be far more than that

Playground Example with a simple cos/sin path -


Your function must just return a radius value.
Example :

var myFunction = function(i, distance) {
  var radius = 3 * Math.cos(distance / 5);
  return radius;
};
var tube = BABYLON.Mesh.CreateTube("lumps", path, null, 20, myFunction, scene);

Here is an example with both an i sinusoidal radius function and x sinusoidal incrementing path : http://www.babylonjs-playground.com/#LG3GS#9 -



Here's another example with a circular path and varying radius : http://www.babylonjs-playground.com/#LG3GS#10 -

Non Regular Polygon

var polygon = BABYLON.Mesh.CreatePolygon("polygon", [V1, V2, ..., Vn], scene, [[V1, V2, ..., Vn], [V1, V2, ..., Vn], ....[V1, V2, ..., Vn]], false, BABYLON.Mesh.DEFAULTSIDE);

Parameters are: name, polygon shape as an array of comma-separated vectors, scene, optional holes as an array of an array of comma-separated vectors, optional updatable and the optional side orientation. The last three parameters can be omitted if you just need the default behavior :

NOTE all vectors are Vector3 and should be in the XoZ plane, ie of the form BABYLON.Vector3(x, 0, z);

var polygon = BABYLON.Mesh.CreatePolygon("cylinder", [V1, V2, ..., Vn], scene);

Uses PolygonMeshBuilder

Extrusion of a Non Regular Polygon

var polygon = BABYLON.Mesh.ExtrudePolygon("polygon", [V1, V2, ..., Vn], 2, scene, [[V1, V2, ..., Vn], [V1, V2, ..., Vn], ....[V1, V2, ..., Vn]], false, BABYLON.Mesh.DEFAULTSIDE);

Parameters are: name, polygon shape as an array of comma-separated vectors, depth, scene, optional holes as an array of an array of comma-separated vectors, optional updatable and the optional side orientation. The last three parameters can be omitted if you just need the default behavior :

NOTE all vectors are Vector3 and should be in the XoZ plane, ie of the form BABYLON.Vector3(x, 0, z) and in counter clockwise order;

var polygon = BABYLON.Mesh.CreatePolygon("polygon", [V1, V2, ..., Vn], 2, scene);

Uses PolygonMeshBuilder

Lines

var lines = BABYLON.Mesh.CreateLines("lines", [
    new BABYLON.Vector3(-10, 0, 0),
    new BABYLON.Vector3(10, 0, 0),
    new BABYLON.Vector3(0, 0, -10),
    new BABYLON.Vector3(0, 0, 10)
], scene);

Parameters are: name, [array of comma-separated vectors], scene.

I could explain how the Lines Mesh constructor works, but I think you can see how it works just by looking at the demo code above. Notice the [ and ]. Those are the enclosing tokens for an array, yet another kind of Javascript value. The first vector3 of the array is the starting location for drawing lines. After that, a comma, and then the next vector3 location... indicating where the line is drawing-to next. Then, another comma, and another vector3 to a new location. You can add as many vectors as you wish, but notice that the LAST vector3 does not have a comma following it. Please make your array of vectors be formatted similarly.

Dashed Lines

var dashedlines = BABYLON.Mesh.CreateDashedLines("dashedLines", [v1, v2, ... vn], dashSize, gapSize, dashNb, scene);

Parameters are : name, [array of Vectors3], dashSize, gapSize, dashNumber, scene.
As for Lines, a line along the vectors3 will be displayed in space. It will try to set dashNumber strokes on this line depending on the length of each segment between two successive vectors3.
dashSize and gapSize are relative to each other dash and gap sizes within these strokes.

Extruded Shape

What is extrusion ?
Extrusion is the way to transform a 2D shape into a volumic shape.
Let's imagine that you define a star shape by filling an array with successive Vector3. In order to have a 2D shape, you only set these points in the xOy plane, so every z coordinate is zero.
ex : http://www.babylonjs-playground.com/#RF9W9 -



Let's show the World axis so it is clearer : http://www.babylonjs-playground.com/#RF9W9#1 -


Let's now imagine you could stretch this 2D shape along the Z-axis to give it some volume... this is extrusion : http://www.babylonjs-playground.com/#RF9W9#30 -

Let's now imagine you can extrude your star along a 3D path in space, a sinus curve for example, and not only along the z-axis.
http://www.babylonjs-playground.com/#RF9W9#31 -


Extrusion can be accomplished with two different methods. A basic one and an advanced or custom one.

BASIC METHOD

BABYLON.Mesh.ExtrudeShape(name, shape, path, scale, rotation, cap, scene, updatable?, sideOrientation)
  • name : the extruded mesh name.
  • shape : the shape to be extruded, an array of successive Vector3.
  • path : the path to extrude the shape along, an array of successive Vector3.
  • scale : default 1, the value to scale the initial shape.
  • rotation : default 0, the step value to rotate the shape at each path point.
  • cap : BABYLON.Mesh.NO_CAP, BABYLON.Mesh.CAP_START, BABYLON.Mesh.CAP_END, BABYLON.Mesh.CAP_ALL.
  • scene : the current scene.
  • updatable? : if the mesh is updatable.
  • sideOrientation : the side orientation - front, back or double.

If we change the scale value from 1 to 3 for example (line 84), the initial star is scaled to 3 along the curve : http://www.babylonjs-playground.com/#RF9W9#526 -


If we now change the rotation step value from 0 to PI / 24 for example, the curve is twisted this angle at each curve point : http://www.babylonjs-playground.com/#RF9W9#218 -

Of course, even if you define your 2D shape in the xOy plane as described, the extrusion still works along any path direction : http://www.babylonjs-playground.com/#RF9W9#32 -


Moreover, the shape doesn't need to be closed. You can have a simple (or complex) open shape : http://www.babylonjs-playground.com/#RF9W9#7 -



Extrusion : http://www.babylonjs-playground.com/#RF9W9#33 -


Extrusion with rotation : http://www.babylonjs-playground.com/#RF9W9#34 -

Remember that your shape doesn't need to be centered on the coordinate system either. Here is an offset simple shape : http://www.babylonjs-playground.com/#RF9W9#10 -



Extrusion (the extrusion path is shown in magenta so the offset is visible) : http://www.babylonjs-playground.com/#RF9W9#35 -


Now rotation... around the path axis : http://www.babylonjs-playground.com/#RF9W9#36 -


As you can see, this is a way to build complex curved helix meshes without handling maths or simpler ones : http://www.babylonjs-playground.com/#RF9W9#37 -


As the shape to be extruded is unpredictable, it is assumed that the cap, if want to add it one or two to your extruded mesh, is computed with its center set to the shape barycenter.

ADVANCED METHOD

BABYLON.Mesh.ExtrudeShapeCustom(name, shape, path, scaleFunction, rotateFunction, ribbonCloseArray, ribbonClosePath, cap, scene)
  • name : the extruded mesh name,
  • shape : the shape to be extruded, an array of successive Vector3.
  • path : the path to extrude the shape along, an array of successive Vector3.
  • scaleFunction : a custom javascript function. This function is called on each path point and is given the i position of the point in the path and its distance from the begining of the path. It must return a scale numeric value. This value will be the scaling applied to the shape drawn at the i-th point.
  • rotationFunction : a custom javascript function. This function is called on each path point and is given the i position of the point in the path and its distance from the begining of the path. It must return a rotation numeric value. This value will be the rotation applied to the shape drawn at the i-th point.
  • ribbonCloseArray : default false, boolean. The underlying ribbon closeArray parameter. This can be used to automatically close a path with right normals computation.
  • ribbonClosePath : default false, boolean. The underlying ribbon closePath parameter. This can be used to automatically close a shape with right normals computation.
  • cap : BABYLON.Mesh.NO_CAP, BABYLON.Mesh.CAP_START, BABYLON.Mesh.CAP_END, BABYLON.Mesh.CAP_ALL.
  • scene : the current scene.
  • updatable? : if the mesh is updatable.
  • sideOrientation : the side orientation - front, back or double.

In this advanced method, the scale and rotation parameters are replaced by custom functions.

scaleFunction
This javascript function will be called on each path point iteration when extruding. It will be passed two parameters : i and distance.

  • i is the point position in the path, starting from zero for the first point.
  • distance is the current point distance from the begining of the path.

This custom function must return a scale numeric value which will be applied to the shape on the i-th point.
Example :

var myScale = function(i, distance) {
  var scale = 2 * Math.sin(i / 5);
  return scale;
};

Here is an example with an unclosed un-centered simple shape whose scale evolves linearly along the path : http://www.babylonjs-playground.com/#RF9W9#38 -



Now if we use a sinus scaling function instead and as the shape isn't centered, we get interesting results : http://www.babylonjs-playground.com/#RF9W9#39 -


We can even emulate rotation by alternately scaling positive/negative : http://www.babylonjs-playground.com/#RF9W9#40 -

rotateFunction
This javascript function will be called on each path point iteration when extruding. It will be passed two parameters : i and distance.

  • i is the point position in the path, starting from zero for the first point.
  • distance is the current point distance from the begining of the path.

This custom function must return a rotation numeric value which will be applied to the shape on the i-th point.
Example :

var myRotation = function(i, distance) {
  var rotation = distance / 20;
  return rotation;
};

Here is an example of constant scale and rotation evolving with the distance : http://www.babylonjs-playground.com/#RF9W9#41 -



You can set a non-linear rotation function of course, sinus here : http://www.babylonjs-playground.com/#RF9W9#42 -

Fixed values

This advanced method needs two custom functions. But you may want to use a custom scale function with a fixed (or no) rotation function, for example. In this case, just pass a custom rotation function returning a fixed value :
Example :

var noRotation = function(i, distance) {
  return 0;
};

If you carefully read the code of this previous example, you can see in line 41 that the scaleFunction returns the constant 1 value : http://www.babylonjs-playground.com/#RF9W9#41 -


ribbonCloseXXX parameters

The extruded mesh is based on an underlying ribbon. When you extrude a shape, you actually make a particular ribbon.
This means you can also set this ribbon closeArray and closePath parameter if you need to automatically close the extruded shape.
NOTE : the closeXXX names are the ribbon ones. Not the extruded shape ones.
So it may be confusing because :

  • ribbonCloseArray set to true will close your shape extrusion path,
  • ribbonClosePath set to true will close your shape itself (if unclosed).

Let's now do this unclosed, un-centered extruded shape : http://www.babylonjs-playground.com/#RF9W9#20 -



And this almost circular path : http://www.babylonjs-playground.com/#RF9W9#21 -


Extrusion with constant scale and no rotation : http://www.babylonjs-playground.com/#RF9W9#43 -


Now let's set the ribbonCloseArray to true :http://www.babylonjs-playground.com/#RF9W9#44 -


As you can see, it closes the extrusion path. Let's set it back to false and let's set the ribbonClosePath to true instead : http://www.babylonjs-playground.com/#RF9W9#45 -


Now the shape is closed.
Both together : http://www.babylonjs-playground.com/#RF9W9#46 -

Summary
At last, the extrude custom function call would be, for example:

BABYLON.Mesh.ExtrudeShapeCustom("extruded", shape, path, myScale, myRotation, false, true, scene)

A shape is an array of successive Vector3. This means 2D or 3D shapes can be extruded as well.
The shape is to be designed in the local coordinate system knowing that the z-axis will be the extrusion path axis.
Finally, shapes don't have to be centered in the local coordinate system.
A centered shape will be extruded symmetrically centered along the path axis. An un-centered shape will be extruded offset from the path axis.

Easy way to generate strange shapes : http://www.babylonjs-playground.com/#RF9W9#47 -


Further Reading

Basic - L1

Mesh Overview
Set Shapes 101
Parametric Shapes 101
Set Shapes
Parametric Shapes
Polyhedra Shapes