Problem
client/src/components/city/CityLights.jsx (~139-159) keeps 12 dynamic pointLights + spot + hemisphere + ambient always live. Zero-intensity lights still cost in the per-fragment lighting loop for every MeshStandardMaterial, so the adaptive-quality low tier cannot shed this cost.
Decision
Conditionally mount the least-visually-significant accent lights (start with the ground-level small-radius pair) only when settings.effectiveTier !== 'low', mirroring the cityShowDetail gating pattern. Requires a quick manual visual check on the low tier before merging (headless can't render — human-in-the-loop verification).
Acceptance
- Low tier renders with reduced light count and no obvious visual regression (screenshot check); full tier unchanged
Problem
client/src/components/city/CityLights.jsx(~139-159) keeps 12 dynamic pointLights + spot + hemisphere + ambient always live. Zero-intensity lights still cost in the per-fragment lighting loop for every MeshStandardMaterial, so the adaptive-quality low tier cannot shed this cost.Decision
Conditionally mount the least-visually-significant accent lights (start with the ground-level small-radius pair) only when
settings.effectiveTier !== 'low', mirroring the cityShowDetail gating pattern. Requires a quick manual visual check on the low tier before merging (headless can't render — human-in-the-loop verification).Acceptance