How glTF Supports Point Primitive Rendering

This article explores the mechanisms glTF uses to support point primitive rendering modes, detailing how the file format defines, structures, and renders point-based geometry such as point clouds. It covers the core mode topology enumeration, accessor data layout, point size handling at the pipeline level, and relevant extension ecosystems that enhance point data delivery.

The Primitive Topology Mode

In glTF (GL Transmission Format), 3D geometry is organized inside a mesh object through an array of primitives. Each primitive defines a mode property, which dictates the topology type used to interpret the vertex data.

While the default topology is 4 (TRIANGLES), glTF natively supports point rendering by assigning the mode value to 0, which maps directly to the OpenGL/WebGL constant POINTS. When mode is set to 0, the rendering engine treats each referenced vertex as an individual, isolated point rather than connecting vertices into lines or triangles.

Vertex Attributes and Accessor Structuring

Point primitives rely on standard glTF data pipelines involving bufferViews and accessors:

  • POSITION Attribute: At minimum, a point primitive requires a POSITION attribute pointing to a tightly packed array of 3D coordinates (typically VEC3 floating-point values).
  • Optional Attributes: Points can be enriched using standard attributes such as COLOR_0 (for per-point coloring, common in photogrammetry scans) and NORMAL (used for oriented points or surfels).
  • Indexed vs. Non-Indexed: Point primitives can be defined without an indices property, meaning the runtime reads sequentially through the attribute arrays. Alternatively, an indices accessor can be provided to reference a specific subset or ordering of points from the underlying vertex buffer.

Point Sizing and Pipeline Execution

The core glTF 2.0 specification defines the topology for points, but it delegates the actual physical on-screen size of the points to the rendering runtime.

In graphics APIs like WebGL, OpenGL, or Vulkan, the vertex shader stage controls point rasterization via parameters like gl_PointSize. When a glTF viewer encounters mode: 0, it typically sets a base point size in pixels or calculates screen-space sizing dynamically based on distance to the camera. For shading, point primitives are frequently paired with the KHR_materials_unlit extension to display raw vertex colors without requiring complex lighting calculations that depend on surface normals.

Compression via Extensions

Because point-based datasets—such as LIDAR scans—often contain millions of individual vertices, glTF leverages the KHR_draco_mesh_compression extension. Draco compression natively supports point cloud encoding, significantly reducing the file size of point primitives by quantizing positions and colors while stripping away unnecessary connectivity data.