Mass and inertia computation

Mass and inertia are computed automatically from particle geometry. For the purposes of rotation integration, inertia is diagonal tensor (and only the diagonal is actually stored) expressed in node-local coordinates (pos and woo.core.Node.ori), therefore nodes might need to be rotated so that mass distribution is aligned with their local coordinate system.

Uninodal particles always have the node in their centroid, and they are oriented along the local axes (e.g. Capsule is always elongated along the local \(+x\)-axis).

Uninodal particles

Uninodal particles have a simplified interface for setting mass and inertia. Particle::updateMassInertia (callable from Python as woo.dem.Particle.updateMassInertia) calls in turn Shape::updateMassInertia passing particle’s material density as parameter.

Multinodal particles

The generic routine Shape::lumpMassInertia collects mass and inertia for given shape and node.

This function is usually invoked throug the static woo.dem.DemData.setOriMassInertia function (which takes woo.core.Node as argument), which collets mass and inertia from all shapes referenced by the node, computes principal axes and aligns node orientation with principal axes; this raises and exception if the shape is orientation-dependent, such as capsule attached to a tetrahedron node.


Clumps implement analytical and numerical (grid-based) computation of centroid, mass, inertia and local orientation.

The analytical method is suitable for clumps without overlaps, where first-momentum is used to compute centroid, second-order momentum and parallel axis theorem to compute inertia tensor eigenvalues and eigenvectors, which are principal axes.

The numerical method is similar, except that it samples the clump with regular grid, and computes each voxel (volume element, grid cell) contribution to mass, first- and second-order momenta. This is suitable for clumps where different shapes are overlapping, since each voxel is only counted once. The numerical routine has different (more efficient) implementation for sphere-only clumps (woo.dem.SphereClumpGeom; testing whether a point is inside is trivial) and another one for generic-shape clumps (woo.dem.RawShapeClump; the point is tested for being inside using the Shape::isInside virtual method).


Got questions? Ask at Report issues to github.