Spaces:
Sleeping
Sleeping
Update README.md
Browse files
README.md
CHANGED
|
@@ -10,6 +10,78 @@ pinned: false
|
|
| 10 |
license: mit
|
| 11 |
short_description: 🧠CV Scroller🧜♀️🧜♂️🧜3D Graphs
|
| 12 |
---
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 13 |
- 🐍 **Python Startup**
|
| 14 |
- 📂 `load_plot_metadata()` → scan `saved_worlds/` for `plot_X…_Z…csv` (cached)
|
| 15 |
- 📑 `load_plot_objects()` → read CSV → build `ALL_INITIAL_OBJECTS`
|
|
@@ -43,4 +115,4 @@ short_description: 🧠CV Scroller🧜♀️🧜♂️🧜3D Graphs
|
|
| 43 |
- 🔄 **Collab Sync**
|
| 44 |
- ⏲️ `setInterval(pollGameState, 5000)` → logs or applies updated `window.GAME_STATE`
|
| 45 |
|
| 46 |
-
✨ **All set!**
|
|
|
|
| 10 |
license: mit
|
| 11 |
short_description: 🧠CV Scroller🧜♀️🧜♂️🧜3D Graphs
|
| 12 |
---
|
| 13 |
+
|
| 14 |
+
|
| 15 |
+
## 📂 File Cast & Roles
|
| 16 |
+
|
| 17 |
+
- **`app.py`** — 🧑✈️ **The Conductor**
|
| 18 |
+
Orchestrates Streamlit:
|
| 19 |
+
- Loads per‑plot CSVs (your saved “tiles”)
|
| 20 |
+
- Fetches the **GameState vault**
|
| 21 |
+
- Injects everything into the browser
|
| 22 |
+
- Listens for your “💾 Save” click and hands new objects off to both the plot‑file writer **and** the GameState vault
|
| 23 |
+
|
| 24 |
+
- **`gamestate.py`** — 💼 **The Vault**
|
| 25 |
+
A thread‑safe singleton that:
|
| 26 |
+
- On startup, reads `world_state.csv` → `world_state[]`
|
| 27 |
+
- On update, merges in new objects by `obj_id` and writes back to `world_state.csv`
|
| 28 |
+
- Serves as the **shared truth** for everyone who joins
|
| 29 |
+
|
| 30 |
+
- **`index.html`** — 🎭 **The Stage**
|
| 31 |
+
Three.js world where:
|
| 32 |
+
- Injected arrays (`ALL_INITIAL_OBJECTS`, `PLOTS_METADATA`, `GAME_STATE`) arrive as `window…` variables
|
| 33 |
+
- Ground tiles and objects are rendered from those arrays
|
| 34 |
+
- Local clicks spawn new objects into a **sessionStorage** “back‑pocket” until you hit Save
|
| 35 |
+
- A tiny 5 s timer peeks at `window.GAME_STATE` so you can see others’ updates in near‑real time
|
| 36 |
+
|
| 37 |
+
- **`requirements.txt`** — 🛠️ **The Toolbox**
|
| 38 |
+
Lists exactly the small helper you need (`streamlit_js_eval`) to bridge JS ↔️ Python
|
| 39 |
+
|
| 40 |
+
---
|
| 41 |
+
|
| 42 |
+
## 🔄 How State Sticks
|
| 43 |
+
|
| 44 |
+
1. **Persistent CSVs**
|
| 45 |
+
- **Per‑plot files** (`plot_X3_Z2.csv`) hold each tile’s snapshot
|
| 46 |
+
- **Global file** (`world_state.csv`) holds the universal list of all objects
|
| 47 |
+
|
| 48 |
+
2. **In‑Memory Caching**
|
| 49 |
+
- `@st.cache_data` for plot metadata (avoids re‑reading disk for 1 h)
|
| 50 |
+
- `@st.cache_resource` for the GameState singleton (one vault, never re‑instantiated)
|
| 51 |
+
|
| 52 |
+
3. **Browser Session Storage**
|
| 53 |
+
- Unsaved objects live in `sessionStorage` so you don’t lose placements on refresh
|
| 54 |
+
- Cleared only when you “Reset” or after a successful Save
|
| 55 |
+
|
| 56 |
+
4. **JS ↔️ Python Bridge**
|
| 57 |
+
- JS `getSaveDataAndPosition()` → returns your new objects + player coords as JSON
|
| 58 |
+
- Streamlit parses that, writes CSV, merges vault, clears caches, and **reruns** to inject the fresh state back into the Stage
|
| 59 |
+
|
| 60 |
+
---
|
| 61 |
+
|
| 62 |
+
## 🌊 Flow of Play (Intuition)
|
| 63 |
+
|
| 64 |
+
1. **Boot Up**
|
| 65 |
+
- Conductor (`app.py`) reads all the saved chunks → tells the Stage (`index.html`) “Here’s what’s out there!”
|
| 66 |
+
|
| 67 |
+
2. **Explore & Build**
|
| 68 |
+
- You walk around (WASD) and click to place “House🌳Rock🏠Tree”
|
| 69 |
+
- New pieces go into your **back pocket** (`sessionStorage`)—invisible until saved
|
| 70 |
+
|
| 71 |
+
3. **Save the Day**
|
| 72 |
+
- Hit “💾 Save” → Conductor grabs your pocket’s contents
|
| 73 |
+
- Vault (`GameState`) merges them into the master record
|
| 74 |
+
- Plot files get updated so new visitors see your work
|
| 75 |
+
|
| 76 |
+
4. **Collaborate in Near‑Real Time**
|
| 77 |
+
- Every 5 s the Stage peeks at `window.GAME_STATE`
|
| 78 |
+
- You see newcomers’ additions pop in without a full reload
|
| 79 |
+
|
| 80 |
+
✨ a tiny toolbox keep a **persistent**, **shared**, **interactive** 3D world humming! 🎉```
|
| 81 |
+
|
| 82 |
+
|
| 83 |
+
|
| 84 |
+
|
| 85 |
- 🐍 **Python Startup**
|
| 86 |
- 📂 `load_plot_metadata()` → scan `saved_worlds/` for `plot_X…_Z…csv` (cached)
|
| 87 |
- 📑 `load_plot_objects()` → read CSV → build `ALL_INITIAL_OBJECTS`
|
|
|
|
| 115 |
- 🔄 **Collab Sync**
|
| 116 |
- ⏲️ `setInterval(pollGameState, 5000)` → logs or applies updated `window.GAME_STATE`
|
| 117 |
|
| 118 |
+
✨ **All set!** end‑to‑end state protocol.
|