Skip to content

Shape Collections

The ShapeCollection is a utility that lets you build complex 2D or 3D geometry by combining predefined shapes, custom meshes, and transformed objects. These collections are typically used with app.mesh() to create a mesh visual.


Overview

  • Add basic geometric shapes: squares, cubes, spheres, etc.
  • Transform each shape independently (offset, scale, 4×4 matrix)
  • Load shapes from .obj files
  • Generate surfaces from height maps or triangulated polygons
  • Use in a mesh visual with lighting, textures, contours, or isolines

Usage

sc = dvz.ShapeCollection()
sc.add_cube(offset=(0, 0, 0), scale=1.0)
visual = app.mesh(sc, lighting=True)

After use, destroy the shape collection to free resources:

sc.destroy()

Supported Shapes

Shape Method Notes
Square add_square() 2D quad in XY plane
Disc add_disc() Circular disc with resolution
Sector add_sector() Arc segment between two angles (2D disc slice)
Cube add_cube() Axis-aligned 3D cube
Sphere add_sphere() Specify rows, cols for resolution
Tetrahedron add_tetrahedron() Platonic solid
Hexahedron add_hexahedron() Cube variant
Octahedron add_octahedron() Platonic solid
Dodecahedron add_dodecahedron() Platonic solid
Icosahedron add_icosahedron() Platonic solid
Cone add_cone() Cone with cap
Cylinder add_cylinder() Cylinder with caps
Arrow add_arrow() Cylinder + cone composite
Torus add_torus() Donut shape with tubular cross-section

Custom Geometry

Polygon

sc.add_polygon(points, contour='full')
  • points: Nx2 array of polygon vertices
  • Uses earcut triangulation internally
  • Contour rendering is experimental

Surface

sc.add_surface(heights, colors)
  • Heights: 2D array of Z-values
  • Colors: 2D RGBA array (same shape)
  • Generates a triangulated surface patch

OBJ Import

Load external 3D geometry from a Wavefront OBJ file:

sc.add_obj("models/teapot.obj", scale=0.5)

This loads all vertices and faces into the shape collection.


Transformations

Each shape can be transformed individually:

  • offset: a 3D translation (x, y, z)
  • scale: a uniform scalar
  • transform: a 4×4 transformation matrix (overrides offset/scale)

Colors

Each basic shape accepts a uniform color argument for the shape.


Finalizing

After building your collection, use:

visual = app.mesh(sc, lighting=True, contour=True)

And after you're done using it:

sc.destroy()   # Frees memory

Example

import numpy as np

import datoviz as dvz

rows = 12
cols = 16
N = rows * cols
t = np.linspace(0, 1, N)

x, y = np.meshgrid(np.linspace(-1, 1, rows), np.linspace(-1, 1, cols))
z = np.zeros_like(x)

offsets = np.c_[x.flat, y.flat, z.flat]
scales = 1.0 / rows * (1 + 0.25 * np.sin(5 * 2 * np.pi * t))
colors = dvz.cmap('hsv', np.mod(t, 1))

sc = dvz.ShapeCollection()
for offset, scale, color in zip(offsets, scales, colors):
    sc.add_cube(offset=offset, scale=scale, color=color)

app = dvz.App()
figure = app.figure()
panel = figure.panel(background=True)
arcball = panel.arcball(initial=(-1, -0.1, -0.25))

visual = app.mesh(sc, lighting=True)

panel.add(visual)

app.run()
app.destroy()
sc.destroy()

Summary

The ShapeCollection system is a powerful way to build reusable geometry for the mesh visual.

  • ✔️ Add and transform 2D/3D primitives
  • ✔️ Generate and combine triangulated surfaces

See also:

  • Mesh for rendering options
  • Volume for dense scalar fields