@tileflow/dev 0.1.0-alpha.37 → 0.1.0-alpha.39

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,179 +0,0 @@
1
- # Prepare recolorable building models
2
-
3
- Custom buildings and landmarks use the same preparation path. Export uncompressed glTF 2.0
4
- binaries in metres, Y up, with the origin on the ground. The default scene's triangles and node
5
- transforms are read. Building preparation retains physical materials and embedded PNG/JPEG
6
- textures. Animations, skins and morph targets are not evaluated; export their static geometry.
7
-
8
- ## Separate colour from architectural role
9
-
10
- Material names select a palette slot: `surface`, `secondary`, `glass`, `accent` or `roof`.
11
- The optional `material.extras.tileflow.lightingRole` selects lighting independently:
12
-
13
- ```json
14
- {
15
- "name": "accent",
16
- "extras": {
17
- "tileflow": {
18
- "lightingRole": "door"
19
- }
20
- },
21
- "pbrMetallicRoughness": {
22
- "baseColorFactor": [0.8, 0.8, 0.8, 1]
23
- }
24
- }
25
- ```
26
-
27
- This door can take the map's `accent` colour while receiving its `door` lighting profile. Accepted
28
- roles are `unclassified`, `wall`, `door`, `roof`, `window`, `lamp` and `logo`. A role describes
29
- geometry; it does not turn on light by itself. The map supplies emission through
30
- `buildings.threeDimensional.modelLighting`.
31
-
32
- Legacy models without an explicit role use these defaults:
33
-
34
- | Palette slot | Lighting role |
35
- | -------------------------------- | ------------- |
36
- | `surface`, `secondary`, `accent` | `wall` |
37
- | `glass` | `window` |
38
- | `roof` | `roof` |
39
-
40
- Doors, lamps and logos require an explicit role. Use `unclassified` for a part that must not inherit
41
- a role. Invalid role names fail preparation. An exporter's numeric material suffix, such as
42
- `surface.001`, is ignored.
43
-
44
- Keep a stone relief in a wall role when it should receive the wall's lighting. A separate colour
45
- slot can distinguish its stone without creating a separate light source. Mark roof geometry as
46
- roof even when it shares a colour with a facade.
47
-
48
- ## Physical materials
49
-
50
- The importer retains these glTF 2.0 channels independently of palette and role:
51
-
52
- | Channel | Inputs |
53
- | ------------------ | --------------------------------------------------------------------------------- |
54
- | Base colour | Linear `baseColorFactor`, linear `COLOR_0` RGB/RGBA, sRGB base-colour texture |
55
- | Reflection | `metallicFactor`, `roughnessFactor`, texture blue/green channels |
56
- | Surface normal | Tangent-space normal texture and `scale`; tangent basis from geometry and UVs |
57
- | Ambient visibility | Occlusion texture red channel and `strength`, multiplied by geometric visibility |
58
- | Emission | Linear `emissiveFactor`, sRGB emissive texture, `KHR_materials_emissive_strength` |
59
- | Coverage | `OPAQUE`, `MASK` with `alphaCutoff`, or `BLEND`; `doubleSided` |
60
- | Unlit | `KHR_materials_unlit` |
61
-
62
- `TEXCOORD_0`, `TEXCOORD_1`, glTF sampler wrapping/filtering and `KHR_texture_transform` are retained.
63
- Every referenced channel must have its declared UV set. UV and colour seams survive welding.
64
- Colour textures and lit output use the scene's gamma-2.2 transfer approximation.
65
- Role emission mixes the complete material radiance toward its target, including authored emission.
66
- Images must be embedded in buffer views or PNG/JPEG data URIs; preparation never fetches external
67
- images. Other image formats and physical-material extensions are not supported.
68
-
69
- Each level accepts at most 256 distinct materials, 32 textures, 4096 pixels per image dimension
70
- and 16,777,216 decoded image pixels in total. The complete prepared file remains limited to 16 MiB.
71
- Invalid references, missing UVs and image headers that disagree with their dimensions fail preparation.
72
-
73
- Without overrides, a physical model retains its authored material. `modelLighting` can tint and
74
- override roughness/metallicity by role. Explicit `modelColors` take precedence over role tints;
75
- textures and vertex colours still modulate the chosen colour. Keep vertex colours neutral when
76
- they should not affect recolouring.
77
-
78
- Colour and normal textures, metallic reflection and alpha coverage use the browser's physical
79
- model path. Ambient visibility never attenuates solar light or emission. Masked pixels also leave
80
- holes in dynamic solar shadows; blended surfaces cast an alpha-tested shadow at 0.5. Transparent
81
- material ranges draw back to front after opaque surfaces; intersecting transparent triangles are
82
- not sorted individually.
83
-
84
- ## Explicit area emitters
85
-
86
- A `door` role lights the surface. To project its spill, declare a rectangle in
87
- `node.extras.tileflow.emitters`. This glTF fragment uses node-local metres and Y up:
88
-
89
- ```json
90
- {
91
- "extras": {
92
- "tileflow": {
93
- "emitters": [
94
- {
95
- "start": [-1, 0, 0],
96
- "end": [1, 0, 0],
97
- "height": 3,
98
- "depth": 0.2,
99
- "role": "door",
100
- "part": "accent"
101
- }
102
- ]
103
- }
104
- }
105
- }
106
- ```
107
-
108
- `start` and `end` form the horizontal lower edge. The spill faces the right of that edge when
109
- viewed from above. `height` sets the rectangle's height; optional `depth` narrows the spill around
110
- recessed jambs. Node transforms apply to the emitter. Its role supplies emission and its part
111
- supplies the fallback palette colour. No emitter is inferred from material colour or geometry.
112
-
113
- Each level accepts 128 emitters. Each projects a four-triangle, depth-tested spill with reach
114
- `clamp(1.3 * height, 4, 10)` metres. This authored effect does not cast a new light or shadow onto
115
- other meshes. It follows the model's visibility and theme; zero emission removes it.
116
-
117
- ## Ambient visibility
118
-
119
- Preparation estimates each vertex's local ambient visibility using 48 deterministic,
120
- cosine-weighted hemisphere samples, a two-metre reach and a two-millimetre origin bias. A spatial
121
- hierarchy limits intersection work; repeated positions and normals share samples. Nearby
122
- occluders contribute more than distant ones. Each level is prepared independently, including
123
- occlusion between its distinct primitives. Footprint meshes do not occlude.
124
-
125
- The result travels independently of colour. Do not bake ambient occlusion into `COLOR_0`: colour
126
- also affects direct sunlight and emission. The runtime applies prepared visibility only to the
127
- ambient contribution; solar visibility still comes from the dynamic shadow map.
128
-
129
- `threeDimensional.modelOcclusion` controls strength from zero to one and defaults to `0.75`.
130
- `threeDimensional.occlusion: false` also disables model ambient occlusion. Changing these
131
- runtime controls does not prepare the geometry again.
132
-
133
- Preparation cost grows with unique vertices, samples and nearby geometry. It is paid when a raw
134
- model is prepared, never per frame. Runtime occlusion adds no draw pass or texture and uses the
135
- existing visibility byte. It describes opaque geometry at rest; it does not follow moving parts,
136
- other models, the ground or surrounding buildings.
137
-
138
- ## Files and compatibility
139
-
140
- Use `<id>.glb`, optionally `<id>.mid.glb` and `<id>.far.glb`. A mesh whose material is `footprint`
141
- defines the area replaced by the model and is not drawn. Otherwise preparation derives a footprint.
142
- See the [Core building guide](https://github.com/tileflow/tileflow-sdk/blob/main/packages/core/docs/buildings-3d.md)
143
- for placement and limits.
144
-
145
- Prepared files retain a 16-byte vertex:
146
-
147
- | Bytes | Content |
148
- | ----- | -------------------------------- |
149
- | 0–5 | Quantized position |
150
- | 6–7 | Padding |
151
- | 8–10 | Normal |
152
- | 11 | Padding |
153
- | 12 | Palette slot |
154
- | 13 | Shade within that slot |
155
- | 14 | Ambient visibility, 0–255 |
156
- | 15 | Architectural lighting role, 0–6 |
157
-
158
- The model root's `extras.tileflow.lightingRoles: 1` declares the last byte. Older files without
159
- that marker use the legacy palette mapping. Existing fully exposed visibility values stay fully
160
- exposed; reprepare the original GLBs to obtain geometric occlusion. Geometry, normals and palette
161
- slots are not modified by the visibility calculation.
162
-
163
- Roles and visibility survive meshoptimizer compression. The existing `_PAINT` accessor and vertex
164
- stride are retained; the role occupies previously unused padding. Prepared files are an SDK
165
- transport format, while material extras are the authoring interface.
166
-
167
- Physical data is optional `extras.tileflow.surface` metadata on each level, with `version: 1`.
168
- Two VEC4 accessors address a separate 32-byte stream: UV0/UV1 followed by linear vertex RGBA.
169
- The metadata also holds material draw ranges, channel references, embedded images and emitters.
170
- Ranges preserve each source mesh's vertical emission bounds independently of its material.
171
- The original primitive layout remains unchanged. Older readers draw its legacy geometry and
172
- palette; they ignore the optional physical data. New readers preserve the legacy shading path
173
- when physical data is absent. Reprepare source GLBs to obtain the new channels.
174
-
175
- The auxiliary stream costs 32 bytes per retained vertex on the GPU. Each resident texture uses
176
- four bytes per pixel, plus about one third for mipmaps when enabled. Decoded images stay available
177
- for context restoration until the model is evicted. Physical materials add one draw per material
178
- range per colour/shadow pass; explicit emitters add one four-triangle draw each. No environment
179
- cube map or screen-space effect is required.
@@ -1,92 +0,0 @@
1
- # Layers inspection
2
-
3
- Open the local preview and select **Layers**. The panel inspects the current map without changing its
4
- authored style. **By module** groups physical layers using compiler contributions; shared layers retain
5
- every owner. **Draw order** lists the renderer's public layer sequence, latest draw calls first.
6
- Custom runtime layers are included even though they are absent from Style JSON. Inspector overlays
7
- are excluded. Unknown ownership is labeled **Unattributed**, rather than guessed from an ID.
8
-
9
- Press **I** or the element-picker icon and click an element on the map. Its layer becomes selected in
10
- Layers and **Rules**, the first detail tab, opens with values evaluated for the picked feature. The
11
- picked feature is a snapshot from that click; changing the layer or artifact/scene revision clears it.
12
- Inspect no longer has a separate top-level tab. Legacy `tab=inspect` links resolve to Layers.
13
-
14
- Enable **Visible only** beside the organization buttons to hide hidden/out-of-zoom layers and vector
15
- layers with no rendered features in the current viewport. The filter combines with search and both
16
- organization modes, and refreshes after camera movement, style changes and tile loading. One viewport
17
- query serves the whole list after a 250 ms pause. During movement the last result remains stable;
18
- failed queries do not classify layers as empty. Custom, raster and background layers remain listed
19
- when their visibility cannot be measured; explicit hidden runtime state is excluded. This is a
20
- rendered-feature filter, not a measurement of final pixels, transparency or occlusion.
21
-
22
- Search by ID, semantic target, module, type, source or source-layer. Click anywhere on a row, or use
23
- Up/Down and Home/End from a focused row. Selection stays in Layers and is retained in the `layer` URL
24
- parameter. If a selected ID disappears, its detail shows that absence and keeps the ID for when it
25
- returns. The Layers tab remains in the existing `tab=layers` parameter.
26
-
27
- ## Read the evidence
28
-
29
- Open **Diagnosis** in the selected layer's detail tabs. With a picked feature or a
30
- Data sample, it explains the filter result and any evaluated zero-size or zero-opacity components.
31
- A zero component is not proof that the whole layer is invisible. Diagnostics findings can open a
32
- specific paint, layout or filter declaration directly in Rules, highlighting its row.
33
-
34
- - **Diagnosis** reports presence, declared visibility, the inclusive minimum/exclusive maximum zoom
35
- range, source loading, shared source tiles and viewport-query observations. Pixel visibility,
36
- occlusion, transparency and depth are explicitly unmeasured. Later draw calls do not necessarily
37
- cover every earlier layer. Runtime 3D controllers report only the state and statistics they expose.
38
- - **Rules** shows paint and layout values inline, without expandable rows, alongside their zoom,
39
- feature, feature-state, global-state and image dependencies. Values use the current zoom and the
40
- picked feature or selected data sample. Edit a value and press Enter or leave the field to preview
41
- it; color pickers update live while open. Enumerations and booleans use selectors. Invalid values
42
- show an error and leave the map unchanged. Edits override the entire physical layer across zooms,
43
- including when a picked feature supplied the evaluated value. Each modified rule has a reset
44
- button that restores its original expression or renderer default. Paint checkboxes temporarily
45
- remove a declaration from the renderer so its default applies. The disabled row stays visible and
46
- crossed out, showing its retained value at the current view; re-enabling restores the exact saved
47
- expression or override. Toggles share edit history and appear in copied context. Implicit defaults
48
- cannot be disabled; edit one to create an explicit rule first. **Undo** and **Redo** beside the
49
- three-dot menu share the temporary style history. **Reset all changes** in that menu restores
50
- temporary style and geometry edits and clears their history. Reload clears temporary edits;
51
- config, source data and build artifacts stay unchanged. Filters remain read-only. Copy context includes the raw rules and temporary edits.
52
- Evaluation does not reproduce placement, transitions or final pixel colors.
53
- - **Data** queries only the selected layer after the viewport settles. At most 80 returned fragments
54
- are retained; the renderer's query itself may return more. Fragments can duplicate logical features
55
- across tile boundaries or world copies. Zero results are not proof that a filter excluded all data.
56
- Unsupported custom/raster/background queries are unavailable, not zero. Choose an actual sample
57
- to inspect its properties, or use **Use for rules** to evaluate that fragment in Rules. Inline
58
- source data is excluded from source details.
59
- - **Origin** preserves sidecar owners, targets, slots and operations. Semantic module paths do not
60
- establish exact source-file or line provenance; token paths appear only if explicitly supplied.
61
-
62
- ## Follow a layer through the map
63
-
64
- Hover or keyboard-focus a layer row to highlight its sampled geometry live in the current map view.
65
- Click a row to keep that layer highlighted. Hovering another row temporarily replaces the highlight;
66
- leaving restores the clicked layer, or clears the preview when no row was clicked. Closing the panel
67
- clears both previews. Hover and click work with the element-picker mode on or off. The camera stays unchanged. The preview refreshes when map movement settles or source tiles
68
- change, even when the hovered layer differs from the selected layer. Hover is coalesced over 80 ms;
69
- queries are cached for the current view. There is no separate **Highlight on map** button.
70
-
71
- Overlays retain at most 30 fragments and 25,000 vertices. They use separate scratch sources and never
72
- change original paint, layout, source data or feature state. A highlight outlines queried geometry;
73
- it is not a reconstruction of glyphs, symbols or 3D meshes. Hidden, out-of-zoom, custom and raster
74
- layers without queryable rendered geometry report that limitation instead of moving the camera.
75
-
76
- **Tiles** inspects tiles grouped by source. Tile costs belong to the shared source, not to a
77
- single style layer. Sprite and font links in Rules open Assets. Other inspection tabs remain usable
78
- while compilation or tile loading continues; obsolete scheduled measurements are discarded.
79
-
80
- ## Give an agent context
81
-
82
- **Copy context** opens a frozen preview in Markdown or JSON. Add an optional investigation question,
83
- then copy it. The packet includes the selected ID, map/theme, generation, scene revision, camera,
84
- viewport, rules, provenance, diagnostic evidence, source, runtime state, recent changes and temporary
85
- edits. It retains at most eight feature property samples, excludes their geometries and inline source
86
- data, removes credentials and query strings from source URLs, and reports projection omissions.
87
- Nothing is sent to an agent automatically.
88
-
89
- While Layers is active, the same observation replaces stale feature selection in the local
90
- `tileflow inspect session --url http://127.0.0.1:3333 --json` context. The CLI applies an additional
91
- bounded projection and reports omitted paths. Temporary edits are observations; capture commands
92
- still use the compiled map rather than reproducing scratch edits.
@@ -1,130 +0,0 @@
1
- # Inspector and compiler inspection
2
-
3
- Start with the [@tileflow/dev guide](https://github.com/tileflow/tileflow-sdk/blob/main/packages/dev/README.md) for installation and a complete first example.
4
-
5
- The CLI opens Inspector through `tileflow preview`. It uses one map and one watched artifact
6
- session by default. The panel groups Map, Layers, Tiles, Assets, Debug and Diagnostics. Camera controls
7
- occupy a separate row below the navigation. Use the three-dot menu to dock left, right or below
8
- the map and choose System, Light or Dark appearance. Drag the divider to resize it; focused dividers
9
- also support arrow keys. Dock position and dimensions persist locally. Layer observations and highlights stay local to the preview. The map fills the remaining
10
- workspace without brand headers or map-status badges. Closing the panel leaves a small **Inspector**
11
- button to reopen it; capture and comparison controls are absent from the interface.
12
-
13
- Add `--against-map ...` or `--against-config ...` for synchronized comparison. Custom local servers
14
- can compose the same shell around existing dev handlers; omit `right` for a single-map session:
15
-
16
- ```ts
17
- import {createTileflowComparisonRequestHandler} from '@tileflow/dev/server';
18
-
19
- const fetch = createTileflowComparisonRequestHandler({
20
- left: {
21
- basePath: '/left',
22
- handler: leftHandler,
23
- label: 'candidate / light',
24
- previewUrl: '/left/',
25
- sidecarUrl: '/left/__inspection/candidate/light.json',
26
- },
27
- right: {
28
- basePath: '/right',
29
- handler: rightHandler,
30
- label: 'reference / light',
31
- previewUrl: '/right/',
32
- sidecarUrl: '/right/__inspection/reference/light.json',
33
- },
34
- });
35
- ```
36
-
37
- Set `fitViewport: true` on each dev handler embedded in a resizable Inspector pane. Scene previews
38
- then fit their pane while captures retain the scene's declared frame. Standalone dev handlers keep
39
- the fixed scene viewport by default.
40
-
41
- Each side handler retains ownership of its styles, fonts, sprites, events, diagnostics, and
42
- last-known-good artifact generation. The comparison router owns the shell, its bundled UI fonts and
43
- strict dispatch to disjoint same-origin route prefixes. An optional `workbench: {url, handle}`
44
- adapter enables theme selection and browser context. Existing CLI capture-record and comparison
45
- APIs remain separate from this interface. Custom servers that omit the adapter retain inspection,
46
- zoom-curve sampling and the sprite atlas. Explicit two-map server configurations retain synchronized
47
- cameras and URL-driven side-by-side/split/overlay/blink layouts without comparison controls.
48
-
49
- See the [human/agent workflow](https://github.com/tileflow/tileflow-sdk/blob/main/packages/cli/docs/map-authoring.md#work-with-a-person-and-an-agent)
50
- for retained evidence, context bounds and `inspect session`. Browser context reports the observed
51
- camera and viewport; capture commands render compiled source without temporary preview edits. The rendered feature summary shows available semantic paths and
52
- keeps raw feature data in a disclosure. It does not infer exact source lines or token ownership.
53
-
54
- Set `inspection: true` on `createTileflowBuildArtifacts` or
55
- `createTileflowArtifactSession` to compute `artifacts.styleInspections[map][theme]`. A dev handler
56
- serves an available sidecar at `/__inspection/<map>/<theme>.json`; otherwise that route is 404. The
57
- option is deliberately off by default. Sidecars remain in memory, do not alter Style bytes or
58
- manifest hashes, and are excluded from `getTileflowArtifactFiles()` and every stable build output.
59
-
60
- When a resolved map declares `fonts`, preparation reads its ordered directories and uses OpenType
61
- full names as the canonical IDs referenced by `text-font`. TTF, OTF, and WOFF2 inputs are supported;
62
- every contributing directory must contain `LICENSE.txt`. Later directories replace earlier faces
63
- with the same exact ID, case-only collisions fail, and every primary font in the final style must be
64
- present. `font` is an exact face ID; local `fallbacks` entries are exact face names or explicit CSS
65
- generic families such as `sans-serif`. Preparation never synthesizes a face name from a family and
66
- weight. Only selected primary faces and licenses are emitted as
67
- content-addressed managed artifacts.
68
-
69
- `fonts` and `glyphs` are mutually exclusive map fields. Omission inherits the parent's current text
70
- provider; declaring either one replaces an inherited provider of either kind atomically. The font
71
- pipeline is driven only by directory metadata and final style usage—there are no hard-coded map or
72
- family names, and a URL provider comes only from the resolved map instead of being invented by the
73
- pipeline. After inheritance resolves, a map with any text layer must have exactly one provider. A
74
- `glyphs: {kind: 'url', ...}` provider enumerates the exact comma-joined MapLibre request keys
75
- produced by the style's `text-font` arrays.
76
-
77
- The resulting style records strict `tileflow:fontFaces` metadata. Preview, capture, and browser
78
- framework adapters load those definitions before constructing MapLibre. Hosted deploy rejects a
79
- prepared local-font bundle before authentication until managed font storage is available. A derived
80
- map that declares `glyphs` replaces the inherited local provider atomically; the URL-backed map is
81
- complete as declared and independent of its World selection.
82
-
83
- ### Pick an element in Layers
84
-
85
- Press **I** or the element-picker icon, hover for a layer/type/ID hint, then click the map.
86
- The clicked element selects its physical layer in **Layers** and opens **Rules**, the first detail tab.
87
- Expression values use that picked feature, rather than an arbitrary viewport sample. **Data** shows
88
- its properties and additional viewport samples; **Use for rules** chooses a different sample.
89
- There is no separate Inspect tab. Legacy `tab=inspect` links open Layers.
90
-
91
- Selecting another layer clears the picked-feature context. Compiler and scene revisions invalidate
92
- old feature snapshots. The renderer's layer ID remains selected across reloads through the `layer`
93
- URL parameter; missing IDs are reported explicitly. Rules expose inline temporary paint/layout
94
- editors for the entire physical layer, with per-rule reset and shared undo history. Preview edits do
95
- not write config, source data or build artifacts. See [Layers inspection](./layers-inspection.md) for diagnostic limits,
96
- map highlighting, provenance and agent context.
97
-
98
- ### Tiles
99
-
100
- **Tiles** shows in-view resident tiles in a spatial grid and source-grouped list, with canonical
101
- `z/x/y`, display zoom, state and raw tile bytes where available. Filter by source or coordinates.
102
- Select a tile to outline its bounds and inspect **Source layers**, **Features** and **Info**.
103
- Source-layer rows link to consuming style layers. Features are paginated in groups of 50 and can
104
- be copied as real GeoJSON. Counts describe tile fragments, including buffer geometry, rather than
105
- unique objects across tiles. **Show on map** fits the selected bounds.
106
-
107
- Raster DEM tiles show decoded grid dimensions and elevation statistics. Raster imagery has no
108
- vector features. Eviction, unavailable internals and unsupported MLT decoding are reported explicitly.
109
- Inspection decodes resident MVT buffers on demand without requesting tiles.
110
-
111
- The view reads the pinned MapLibre renderer's tile managers through an isolated adapter. A resident
112
- tile can come from cache and need not have a new HTTP request. Unsupported renderer internals
113
- produce an unavailable state. Network does not list application scripts, development-server
114
- traffic or other HTTP resources. Sprite and font sources remain in **Assets**.
115
-
116
- ### Assets and debug overlays
117
-
118
- **Assets** separates Icons, 3D models and Fonts. Icons lists registered images, including runtime
119
- additions, with lazy thumbnails and searchable IDs. Theme and time-of-day filters load the actual
120
- registered theme atlases; the selected icon's sidebar compares its day/night variants and links to
121
- consuming layers. Missing variants are marked, never synthesized from a naming convention.
122
-
123
- 3D models previews bounded samples of the actual loaded building and vegetation meshes. Counts,
124
- bytes, LODs and available instance counts describe controller data. The wire geometry preview is
125
- not the map's lighting renderer. Fonts renders editable specimens from the actual font or glyph
126
- provider and shows observed glyph ranges and consuming layers. Pending requests are cancelled
127
- when leaving the panel; unavailable sources do not silently use a fallback font.
128
-
129
- **Debug** offers collision boxes, overdraw with a color legend, tile boundaries and real pixel-ratio
130
- controls. **Diagnostics** lists design findings and optional drawing-cost observations; see [Map design diagnostics](./map-design-diagnostics.md).
@@ -1,76 +0,0 @@
1
- # Map design diagnostics
2
-
3
- Open **Diagnostics** in Inspector to investigate a map's rules, visual resources and current-view
4
- composition. The list groups findings under **Readability**, **Style**, **Assets** and **Performance**.
5
- **Problem** means a confirmed configuration or resource failure. **Review** means an observed
6
- situation may be intentional. Counts refer to grouped findings, not quality scores.
7
-
8
- ## Check the map
9
-
10
- Style observations refresh after changes settle. **Check view** explicitly collects samples from
11
- the current map and briefly profiles drawing work. It does not navigate to other cities, change the
12
- camera, compile themes or save edits. Changing the map or leaving the panel cancels pending work.
13
- Expensive renderer observations are not repeated continuously while editing colors or dragging.
14
-
15
- The initial detectors cover invalid style rules, broken references and zoom ranges, unresolved
16
- icons, verifiable text contrast, large layer stacks, potentially repeated rules and drawing work.
17
- Findings group affected layers and keep bounded examples. A missing image must remain unresolved
18
- after loading; images with a working fallback are not missing resources. An empty viewport or a
19
- layer outside its zoom range does not by itself create a global problem.
20
-
21
- Text contrast is checked only where the evaluated text and opaque halo make the color pair
22
- verifiable. This is not a measurement of all pixels behind a label or certification that a map is
23
- readable. Unavailable evaluation context does not become a passing observation. Size thresholds,
24
- absence of halos and ordinary collision rejection do not establish design defects.
25
-
26
- Performance findings are review indications. A style layer, a queried feature, a draw call and an
27
- overdraw pass measure different things. Layer stacks are grouped by compiler provenance when it is
28
- available; unknown ownership is not inferred from names. Equivalent drawing rules may be deliberate
29
- casings, shadows or blending, so they are never automatically removed. Counts and short CPU samples
30
- do not attribute GPU cost to an individual layer or establish a universal performance grade.
31
-
32
- Native overdraw is observed only when the renderer and scene permit a meaningful measurement.
33
- Custom rendering, terrain, sky, globe projection or active debug modes can make it unavailable. The native sample saturates
34
- at eight passes, so an eight-pass observation is a lower bound. Sampling temporarily enables the
35
- native debug rendering and restores it; open **Debug** explicitly to keep an overlay visible.
36
-
37
- Drawing-work sampling requests repaints for approximately 650 ms and requires at least ten complete
38
- frames. Compatible native overdraw sampling has a separate two-second limit. A median of at least
39
- 1,000 draw submissions, or at least 25% of sampled pixels reaching eight passes, creates a review
40
- finding. These are disclosed review triggers, not universal limits. Label evaluation and retained
41
- examples are capped; reading the style and querying rendered features still depend on map size.
42
- Detailed rule checks inspect at most 2,000 non-internal layers, while stack counts include the
43
- whole style. Contrast sampling retains up to 5,000 symbol candidates, evaluates at most 200 of
44
- them and keeps up to 40 eligible examples. Coverage limits remain available in the copied report.
45
-
46
- ## Investigate a finding
47
-
48
- Expand a row to read its evidence and limitations. **Open rule** selects the layer and focuses the
49
- related paint, layout or filter declaration. **Show on map** uses the finding's observed context;
50
- asset and overdraw actions open the corresponding inspection tools. Available actions depend on
51
- the evidence. Preview changes remain temporary and share Undo/Redo and Reset all changes.
52
-
53
- Findings retain the map revision and camera in which they were observed. Moving away is not proof
54
- that a problem was fixed. Old view evidence is marked stale until checked again. Local dismissals
55
- apply to a case fingerprint; changing the relevant evidence makes it reviewable again. Incomplete
56
- checks and missing renderer capabilities are included in the copied report.
57
-
58
- **Copy findings** and each finding's copy action include structured evidence, conditions and
59
- temporary edits. Context is sanitized, bounded and reports omissions. Nothing is sent to an agent
60
- automatically. The output is diagnostic evidence, not a benchmark or release certification.
61
-
62
- ## Explain a layer's visibility
63
-
64
- Select a layer in **Layers**, then open **Diagnosis**. It shows declared visibility,
65
- zoom eligibility, source state and viewport-query observations. With an actual selected feature it
66
- also evaluates its filter and relevant zero-size or zero-opacity rules. A zero component does not
67
- prove the whole layer is invisible: a circle stroke or another symbol component may still draw.
68
- Unknown expression context and geometry-dependent filters remain unavailable. Query matches do
69
- not establish final pixel visibility, depth or occlusion.
70
-
71
- ## Compatibility
72
-
73
- The tab persists as `tab=diagnostics`. Previous `tab=beacon` links open the new panel. The former
74
- Beacon scoring and tour interface is retired; its historical report scores are not comparable to
75
- Diagnostics findings. Network infrastructure, platform regressions and broad map quality remain
76
- separate concerns from these author-facing checks.