Skip to content

Minimal Tier-M geometry: a JSON triangle mesh + tier-selective loading#130

Open
louistrue wants to merge 1 commit into
buildingSMART:mainfrom
LTplus-AG:louistrue-mesh-core
Open

Minimal Tier-M geometry: a JSON triangle mesh + tier-selective loading#130
louistrue wants to merge 1 commit into
buildingSMART:mainfrom
LTplus-AG:louistrue-mesh-core

Conversation

@louistrue

@louistrue louistrue commented Jul 2, 2026

Copy link
Copy Markdown

Minimal Tier-M geometry: a JSON triangle mesh + tier-selective loading

Following the ADR 6 (https://github.com/buildingSMART/IFCX-CORE/issues/6) discussion (geometry representations), this proposes the smallest useful geometry core as code (types + behaviour + tests): a minimal JSON triangle mesh and the tier routing contract around it, nothing USD- or glTF-runtime-specific.

It's deliberately scoped to what the thread converged on ("the simplest triangle mesh we can think of serialized as JSON", mapping cleanly to both USD and glTF without forcing consumers to implement either runtime). Procedural and Brep tiers are out of scope here and proposed separately.

This PR intentionally touches src/ only, it does not add a normative schema yet (see "Schema" below), so the representation can be discussed before we fix its serialized form.

What's in it

  • DisplayMesh (TS type): points + faceVertexIndices (triangles only), optional normals/uvs, and provenance (derivedFrom, sourceHash, faceGroups). The triangle geometry maps directly to a triangulated UsdGeomMesh and a glTF triangle primitive (face counts implicit; positions as authored, subject to glTF float precision); the provenance fields ride in glTF extras / USD custom attributes. Consumable by any JSON/HTTP client with no USD/glTF runtime.
  • TierResolver: tier-selective loading with an access log: by construction a resolver asked only for Tier M never reads another tier's table (a test asserts the procedural table is refused even on an explicit cross-tier request).
  • AttributeTable: the NDJSON one-row-per-line table primitive the tiers are addressed through (aligns with the "index → separate attribute records" shape in Post alpha #105).

DisplayMesh.sourceHash is kept as an opaque field; the content-hashing scheme (for staleness/deltas) is proposed separately, alongside the code that produces it, to keep this PR to the mesh representation.

No dependency on the procedural / Brep / external catalogs, those are keys in the routing taxonomy only. ~270 lines, tests included, builds and runs green with no new runtime dependency.

Open questions this is meant to settle (from the ADR 6 thread)

  • vs IfcTriangulatedFaceSet-as-JSON (@TLiebich): happy to align field names / drop PnIndex — the intent is the minimal subset, so if a JSON serialization of IfcTriangulatedFaceSet is the preferred basis, this is a starting point to converge on, not a competing invention.
  • face vs vertex colours (@aothms): this carries no colour on the mesh and leaves presentation to material binding. If non-semantic colours are wanted (GIS / scan-to-BIM / annotation), I'd add them explicitly rather than inherit USD's primvar complexity — flagging for a decision.
  • ISO-referenceability (@TLiebich): because it's plain JSON that maps to glTF (ISO/IEC 12113) as well as USD, it avoids a normative dependency on OpenUSD's licensing/standardisation status.

Schema (deliberately deferred)

I did not add a schema file, to avoid pre-deciding its format: current main defines schemas as TypeSpec under schema/, while #105 moves toward JSON-schema + OpenAPI. Once the mesh shape is agreed I'll add the normative schema in whichever form the project settles on. $id / versioning / namespace follow the same decision.

The external tier is reserved in the routing taxonomy but ships no payload here (opaque interop reference, proposed separately).

Wider context (not in this PR)

The fuller tiered story with Brep topology as identity-bearing nodes (relevant to ADR 3 identity), procedural authoring intent, importers, viewer all lives on a separate branch in my fork and in the ADR 6 / 3 threads. This PR is just the minimal, mergeable mesh slice.

A minimal, dependency-free geometry core for IFCX, aligned with the ADR buildingSMART#6
direction toward a simple JSON mesh rather than a full USD/glTF runtime contract:

- DisplayMesh: a minimal JSON triangle mesh (points + triangle indices, optional
  normals/uvs and provenance). Maps losslessly to UsdGeomMesh and to glTF, and is
  consumable by any JSON/HTTP client with no USD or glTF runtime.
- TierResolver: tier-selective loading with an access log — a consumer that
  requests only Tier M provably never reads any other tier's table.
- AttributeTable: the NDJSON one-row-per-line table primitive.
- source-hash: RFC 8785 (JCS) canonicalisation + SHA-256, "sha256-<hex>" (SRI
  convention), for content-addressed staleness/change detection.
- JSON schema for DisplayMesh; tests for all of the above.

No dependency on the procedural/Brep/external catalogs — those tiers are keys in
the routing taxonomy only, proposed separately.
@louistrue louistrue force-pushed the louistrue-mesh-core branch from 9bddca5 to 56eab75 Compare July 2, 2026 17:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant