Files
settled-reach/client/ui/implant/apps/atlas/atlas_generation_state.gd
T
jpmschweitzerandClaude Fable 5 e41cca2ded feat(ui): T-1118 climate overlay + T-1119 quarter glyphs — client halves, with file-size extractions
T-1118: gen_region_grid overlay (label TMP) — _draw_gen_region_grid
copies _draw_gen_district's self-contained mapping (dims from the
layer dict); mean-temp cold-to-hot ramp over -50..+50 C;
REGION_TEMP_NONE_DC airless sentinel = skip-cell (undrawn, never an
invented color); legend entry.

T-1119 (touch points 3-6): quarter_footprints protocol passthrough;
gen_l4_quarters overlay (label QTR) — density-scaled glyph anchored
on the L3 settlement dot joined by city_id, shape = dominant district
type (corner-tab/diamond marks for Commercial/Industrial/
Administrative), color = density ramp on the settlement-gold family,
zoom-gated at SETTLEMENT_LABEL_MIN_ZOOM; landmark/corridor counts
never drawn (D-226(d) tooltip-only ceiling); legend entry.

Structure: atlas_viewer.gd and protocol.gd were over gdlint's
1000-line cap before this batch; cleanly-separable responsibilities
extracted on existing precedent — atlas_generation_state.gd (per-layer
data + accessors), atlas_generation_proxy.gd (polling/retry/pending
machinery), atlas_overlay_colors.gd (pure ramp/shape lookups),
atlas_map_protocol.gd (atlas/starmap/citynames codec, the
browse_protocol.gd delegate pattern). Public APIs preserved exactly;
_gen_state stays a field default (RefCounted, pre-_ready safe) because
_ready()-construction breaks every bare AtlasViewer.new() test —
documented inline.

Tests: registration + round-trip for both overlays; pure-function
suites for the temp ramp (endpoints/midpoint/clamp/sentinel) and
quarter glyph (scaling, zoom gate, ramp, notch across all 9
DistrictTypes); Tier-2 replay asserts exact literals from the real
server-generated fixture incl. the airless sentinel. Color.lerp(a,b,
1.0) is not bit-exact to b — endpoint assertions use per-component
is_equal_approx. Full suite 3094/3094; gdlint zero warnings incl. the
two previously-over-cap files. Live capture: legend grows to 7
sections, TMP/QTR toggles clean against a live server.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-18 12:25:47 +02:00

106 lines
3.4 KiB
GDScript

extends RefCounted
## Generation-cascade layer state for AtlasViewer (#960, D-225).
##
## Extracted from atlas_viewer.gd (T-1118/T-1119) to keep that file under the
## gdlint max-file-lines cap while it keeps growing a new field+accessor pair
## per generation layer (layer1, district_grid, road_graph, settlements,
## region_grid, quarter_footprints — the AtlasLayerResponse growth-ceiling
## note in the D-226 T-1112 amendment names region_grid/quarter_footprints as
## the last two candidate sibling Option fields). One `_generation_*` field +
## one get/set pair per layer, all following the same "store + redraw the
## overlay" shape — collecting them here means that shape is written once
## (in _set) instead of once per accessor pair.
##
## AtlasViewer holds one instance (`_gen_state`) and exposes the SAME public
## get_generation_*()/set_generation_*() method names it always has —
## external callers (atlas_marker_overlay.gd, test_atlas_overlays.gd) are
## unaffected; only the storage moved. Consumed via explicit load() by path
## (no class_name), matching atlas_legend_panel.gd/atlas_overlay_bar.gd
## (review #8 there): AtlasViewer is itself referenced by class_name in
## other scripts, and a second global class_name in this cluster is an
## unnecessary addition to the global class cache.
var _overlay_node: Node2D = null # set once by AtlasViewer._ready() (the redraw target)
var _layer1: Variant = null # #960: Layer1Output from the proxy (D-225)
var _district_grid: Variant = null # T-1046: coarse DistrictGridLayer (D-226)
var _road_graph: Variant = null # T-960: RoadGraph layer from the proxy (D-225)
var _settlements: Variant = null # T-960: settlement placements from the proxy (D-225)
var _region_grid: Variant = null # T-1118: RegionGridLayer climate grid (D-226/T-1113)
var _quarter_footprints: Variant = null # T-1119: QuarterFootprintLayer (D-226 T-1112 amendment)
func bind_overlay_node(overlay_node: Node2D) -> void:
_overlay_node = overlay_node
func _redraw() -> void:
if _overlay_node:
_overlay_node.queue_redraw()
## Reset every layer to its pre-body-load default. Called from
## AtlasViewer.show_body() so a body switch doesn't inherit the previous
## body's generation data.
func reset_layer1() -> void:
_layer1 = null
func set_layer1(layer1: Variant) -> void:
_layer1 = layer1
_redraw()
func get_layer1() -> Variant:
return _layer1
func set_district_grid(grid: Variant) -> void:
_district_grid = grid
_redraw()
func get_district_grid() -> Variant:
return _district_grid
func set_road_graph(graph: Variant) -> void:
_road_graph = graph
_redraw()
func get_road_graph() -> Variant:
return _road_graph
func set_settlements(settlements: Variant) -> void:
_settlements = settlements
_redraw()
func get_settlements() -> Variant:
return _settlements
## T-1118: store the region climate grid (RegionGridLayer) from the proxy and
## redraw. The marker overlay reads it via AtlasViewer.get_generation_region_grid().
func set_region_grid(grid: Variant) -> void:
_region_grid = grid
_redraw()
func get_region_grid() -> Variant:
return _region_grid
## T-1119: store the L4 quarter-footprint aggregates (QuarterFootprintLayer)
## from the proxy and redraw. The marker overlay reads it via
## AtlasViewer.get_generation_quarter_footprints().
func set_quarter_footprints(footprints: Variant) -> void:
_quarter_footprints = footprints
_redraw()
func get_quarter_footprints() -> Variant:
return _quarter_footprints