feat(assets): procedural planet renders for wiki/GTTR — #779
7 planet type PNGs (512×512px RGBA) covering all biome_summary values: temperate, temperate_terminator, oceanic, arid, frozen, volcanic, barren. Pure Python ray-sphere renderer (spikes/planet-renders/generate_planets.py) — numpy/PIL only, no Godot dependency, ~2s for all 7 types. Seeded from body_id for reproducibility. Resolves Q-064 (Godot 3D planet plugin evaluation — superseded by headless Python approach). Assets at client/assets/planets/, 512×512 RGBA, displayed at 240×240 in the body-info-panel navigator and GTTR arrival window. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,157 @@
|
||||
---
|
||||
title: "Planetary Screenshot Spec — v0.1"
|
||||
description: "Procedural planet sphere renders for the GTTR body-info-panel and wiki pages. One image per biome_summary type."
|
||||
type: design
|
||||
status: active
|
||||
ticket: "#779"
|
||||
decision_refs: []
|
||||
author: "Araminta"
|
||||
created: 2026-04-05
|
||||
updated: 2026-04-05
|
||||
---
|
||||
|
||||
# Planetary Screenshot Spec — v0.1
|
||||
|
||||
**Ticket:** #779
|
||||
**Author:** Araminta
|
||||
**Date:** 2026-04-05
|
||||
**Status:** Active — assets delivered, awaiting client integration
|
||||
|
||||
---
|
||||
|
||||
## Display Context
|
||||
|
||||
Planet screenshots appear in the **body-info-panel** navigator (wireframe:
|
||||
`docs/design/wireframes/navigator/body-info-panel.json`):
|
||||
|
||||
| Property | Value |
|
||||
|----------|-------|
|
||||
| Container | `planet-screenshot` — 360×360px, `#111820` background |
|
||||
| Sphere display | 240×240px ellipse within the container |
|
||||
| Z-context | Implant fullscreen (z=20), not gameplay layer |
|
||||
| Background | `#0d1117` (navigator panel) |
|
||||
|
||||
In the **GTTR arrival window** (diegetic implant display during transit), the same
|
||||
asset appears with the same proportions — one image per destination planet.
|
||||
|
||||
---
|
||||
|
||||
## Asset Inventory
|
||||
|
||||
**Location:** `client/assets/planets/`
|
||||
**Format:** PNG, 512×512px, RGBA
|
||||
**Display:** Scaled to 240×240 within a 360×360 container
|
||||
|
||||
| File | `biome_summary` value | Character |
|
||||
|------|-----------------------|-----------|
|
||||
| `planet_temperate.png` | `temperate` | Blue ocean, amber-green continents, cloud cover, polar caps |
|
||||
| `planet_temperate_terminator.png` | `temperate_terminator` | Half gold-scorched day face, half frozen dark face, sharp terminator |
|
||||
| `planet_oceanic.png` | `oceanic` | Deep blue water world, heavy cloud, scattered archipelago |
|
||||
| `planet_arid.png` | `arid` | Warm reddish-brown, dusty, sparse thin polar caps |
|
||||
| `planet_frozen.png` | `frozen` | White-blue ice, exposed grey rock at mid-latitudes |
|
||||
| `planet_volcanic.png` | `volcanic` | Dark basalt, orange lava cloud patterns |
|
||||
| `planet_barren.png` | `barren` | Cratered grey-brown, no atmosphere glow |
|
||||
|
||||
---
|
||||
|
||||
## Generation Pipeline
|
||||
|
||||
**Script:** `spikes/planet-renders/generate_planets.py`
|
||||
|
||||
```bash
|
||||
# Regenerate all types
|
||||
python3 spikes/planet-renders/generate_planets.py
|
||||
|
||||
# Single type
|
||||
python3 spikes/planet-renders/generate_planets.py --type temperate
|
||||
|
||||
# Custom output location
|
||||
python3 spikes/planet-renders/generate_planets.py --output-dir path/to/dir
|
||||
```
|
||||
|
||||
**Dependencies:** `numpy`, `Pillow` (already in requirements)
|
||||
|
||||
**Technique:** Numpy ray-sphere intersection + Lambertian diffuse + specular +
|
||||
procedural octave-sine texture. Runs without GPU. ~2s for all 7 types.
|
||||
|
||||
### Lighting rig
|
||||
|
||||
| Property | Value |
|
||||
|----------|-------|
|
||||
| Star direction (from surface) | (-0.55, 0.45, 0.70) normalized |
|
||||
| Ambient | 0.22 (dark side is dim, not black) |
|
||||
| Diffuse | 0.78 |
|
||||
| Specular | 0.30 (modest glint) |
|
||||
| Atmosphere rim glow | Blue-white, (1-rim)^5 × 0.7 |
|
||||
|
||||
### Texture approach
|
||||
|
||||
Procedural octave sine noise — no external noise library required. UV coordinates
|
||||
from spherical mapping (lon, lat). Each planet type uses different:
|
||||
- `seed` (shifts continent/feature pattern)
|
||||
- `octaves` (detail level)
|
||||
- `threshold` (land/ocean boundary)
|
||||
- Color palette (per type)
|
||||
|
||||
---
|
||||
|
||||
## Binding to Atlas Data
|
||||
|
||||
Each planet in `systems.db` has a `biome_summary` field. The client selects the
|
||||
matching planet image:
|
||||
|
||||
```gdscript
|
||||
func planet_image_for_biome(biome: String) -> Texture2D:
|
||||
var path = "res://assets/planets/planet_%s.png" % biome
|
||||
if ResourceLoader.exists(path):
|
||||
return load(path)
|
||||
return load("res://assets/planets/planet_barren.png") # fallback
|
||||
```
|
||||
|
||||
For `biome_summary = "temperate_terminator"`, the image maps directly to
|
||||
`planet_temperate_terminator.png`.
|
||||
|
||||
---
|
||||
|
||||
## Coverage
|
||||
|
||||
| `biome_summary` value | Image | Inhabited planets using this type |
|
||||
|-----------------------|-------|------------------------------------|
|
||||
| `temperate` | ✓ | Majority of wave_1/wave_2 inhabited worlds |
|
||||
| `temperate_terminator` | ✓ | Close-orbit M-dwarf worlds (Feldmark, Caparica) |
|
||||
| `oceanic` | ✓ | Aquaculture worlds |
|
||||
| `arid` | ✓ | Mars-analog, dry inner worlds |
|
||||
| `frozen` | ✓ | Outer habitable zone, cold worlds |
|
||||
| `volcanic` | ✓ | Young volcanic, active worlds |
|
||||
| `barren` | ✓ | Airless rocky bodies, uninhabited |
|
||||
| `gas_giant` | — | Not needed (gas giants not inhabited, no panel) |
|
||||
|
||||
---
|
||||
|
||||
## Visual Grammar Notes
|
||||
|
||||
All planet renders are consistent with the implant UI aesthetic:
|
||||
|
||||
- **Background:** `#04060a` space (near-black, matches `#0d1117` panel)
|
||||
- **Star field:** Sparse white dots, random but seeded (reproducible)
|
||||
- **Atmosphere rim:** Blue-white glow on all worlds with atmosphere — signals
|
||||
habitability/breathability at a glance
|
||||
- **Terminator worlds:** Gold/dark split communicates the concept without labels
|
||||
- **Barren worlds:** No rim glow — instantly reads as airless
|
||||
|
||||
The renders are deliberately non-photorealistic. They're what the player's implant
|
||||
processes during transit — a data-layer visualization, not a photograph.
|
||||
|
||||
---
|
||||
|
||||
## Future Additions
|
||||
|
||||
When new `biome_summary` types are added to the atlas schema, add a new renderer
|
||||
function to `generate_planets.py` following the existing pattern. The functions
|
||||
are self-contained — no cross-dependencies.
|
||||
|
||||
Potential additions as the Reach fills out:
|
||||
- `jungle` — dense green, high cloud, equatorial band
|
||||
- `desert` (distinct from `arid` — hotter, brighter orange)
|
||||
- `swamp` — dark green-brown
|
||||
- `gas_giant_banded` — for the implant wiki page of orbital gas giants
|
||||
Reference in New Issue
Block a user