perf(FragmentsModels): fill tiles in size-sorted sample order to cut visibility runs - #282
Open
rihokirss wants to merge 1 commit into
Open
perf(FragmentsModels): fill tiles in size-sorted sample order to cut visibility runs#282rihokirss wants to merge 1 commit into
rihokirss wants to merge 1 commit into
Conversation
…visibility runs A tile's index buffer is laid out in the order samples were appended and the per-sample LOD decision depends on screen size, so with file-ordered samples the geometry / wires / invisible cut through a tile produced dozens of interleaved visibility runs. Each run becomes a geometry.groups entry on the main thread, i.e. its own draw call. Feeding generate() the existing size-sorted _samplesDimensions order keeps the cut to one or two runs. Tile membership and geometry are unchanged.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Part of #278.
generate()fills tiles by walking samples0..N(file order), whilefetchLodLeveldecides per sample from its screen size. The two orders are unrelated, so the geometry / wires / invisible cut through a tile lands as dozens of interleaved visibility runs — and every run becomes ageometry.group, i.e. a draw call._samplesDimensionsalready exists and is already sorted big → small (it is the orderupdateTilessweeps in, built inprocessSamplesDimension()duringinit(), which runs beforegenerate()). Feeding tile construction that same order keeps samples of similar size — and therefore of the same LOD level at any given camera distance — adjacent inside a tile, so the cut is one or two runs.Tile membership, tile ids, geometry and the per-sample classification are unchanged; only the order of samples inside a tile's index buffer differs.
Measurements
Headless Chromium, Radeon 780M, 1920×1080, postproduction off, 50 FPS cap, medians of 3 runs.
geometry.groups, 1 modelgeometry.groups, 8 modelsRendered content is the same; the screenshot diff is ≤0.08 % of pixels and is entirely one façade strip where two coplanar surfaces z-fight — the tile that arrives first wins, and this changes tile order. No difference anywhere else.
This composes with the compacted-index PR (which removes the remaining runs on the main thread): together the 8-model scene runs at 1 817 draw calls and the 50 FPS cap.
The companion PR for #278 is #281 (main-thread index compaction). They are independent — either can go in alone — and compose.
🤖 Generated with Claude Code
https://claude.ai/code/session_013rtNQqhSQRM2t6E98DESNE