Fix OSM multipolygon buildings

This commit is contained in:
2026-08-03 18:15:22 +08:00
parent 37fe65b7ca
commit 95f8458ad2
11 changed files with 458 additions and 18 deletions

View File

@@ -0,0 +1 @@
{"_example": "Fill with {\"file\": \"<path>\", \"reason\": \"<why>\"}. Put spec/research files only — no code paths. Run `python3 .trellis/scripts/get_context.py --mode packages` to list available specs. Delete this line once real entries are added."}

View File

@@ -0,0 +1 @@
{"_example": "Fill with {\"file\": \"<path>\", \"reason\": \"<why>\"}. Put spec/research files only — no code paths. Run `python3 .trellis/scripts/get_context.py --mode packages` to list available specs. Delete this line once real entries are added."}

View File

@@ -0,0 +1,39 @@
# Fix OSM multipolygon building rendering
## Goal
Fix Blender scene generation so OSM `type=multipolygon` building relations are
rendered as buildings, and explicit OSM `height` tags are respected for normal
buildings.
## Requirements
1. Parse OSM multipolygon relations whose relation tags include `building=*`.
2. Use relation-level tags, including `height`, when generating the building.
3. Support the common case of closed outer way members and closed inner way
members, as seen in nantaizi `relation -65`.
4. Keep existing way-based building rendering working.
5. Change building height semantics so an explicit `height` tag controls render
height; fallback office default `11.4m` should apply only when height is not
explicitly present and the building is not industrial / tall.
6. Validate only `nantaizi-lake-innovation-valley`.
## Acceptance Criteria
- [x] `parse_osm()` exposes the nantaizi building multipolygon relation as a
renderable building feature.
- [x] Unit tests cover relation-level building tags, outer/inner members, and
malformed / incomplete relation members.
- [x] Existing way-based building parsing tests still pass.
- [x] A relation building with `height=8` renders at `8m`, not the office
fallback `11.4m`.
- [x] nantaizi Blender generation succeeds and includes the multipolygon
building in counts / scene digest.
- [x] No hanyang validation is required unless requested.
## Notes
- Concrete reproduction in current input:
`relation -65` has `building=yes`, `height=8`, `type=multipolygon`, outer way
`-2948`, and inner way `-2952`. The member ways carry no building tags, so the
current way-only dispatcher skips it.

View File

@@ -0,0 +1,48 @@
# Multipolygon building fix report
## Root Cause
The edited nantaizi OSM has `relation -65` with:
- `type=multipolygon`
- `building=yes`
- `height=8`
- outer way `-2948`
- inner way `-2952`
The member ways have no building tags. `parse_osm()` only exposed ways, and
`generate_scene.py` only dispatched ways, so the relation was skipped.
The height issue had a second cause: ordinary non-industrial buildings below
`30m` were forced to the office fallback render height `11.4m`, even when OSM
had an explicit `height`.
## Implemented
- `parse_osm()` now exposes building multipolygon relations as synthetic
building features with relation-level tags and `inner_coords`.
- Open relation member way fragments can be stitched into closed rings; malformed
relation leftovers are skipped without aborting parsing.
- `generate_scene.py` passes projected `inner_rings` to building assembly.
- `building.py` creates prism and roof meshes with holes using Blender
tessellation.
- Explicit OSM `height` now controls render height. The `11.4m` office fallback
applies only when height is not explicit.
## Validation
- `python3 -m unittest discover blender/tests`
- `npm run build:area -- --config config/areas/nantaizi-lake-innovation-valley.json --stages blender`
- `npm run build:area -- --config config/areas/nantaizi-lake-innovation-valley.json --stages cesium`
- `node scripts/glb-digest.js outputs/nantaizi-lake-innovation-valley/nantaizi-lake-innovation-valley.glb`
- `python3 ./.trellis/scripts/task.py validate .trellis/tasks/08-03-fix-osm-multipolygon-buildings`
- `git diff --check`
Confirmed `Building_-65` in scene and GLB:
- `osm_height=8`
- `render_height=8`
- GLB contains `Building_-65`, `Building_-65_Roof`, and
`Building_-65_Windows`
User verified the result visually in preview.

View File

@@ -0,0 +1,26 @@
{
"id": "fix-osm-multipolygon-buildings",
"name": "fix-osm-multipolygon-buildings",
"title": "Fix OSM multipolygon building rendering",
"description": "",
"status": "in_progress",
"dev_type": null,
"scope": null,
"package": null,
"priority": "P2",
"creator": "dingkang",
"assignee": "dingkang",
"createdAt": "2026-08-03",
"completedAt": null,
"branch": null,
"base_branch": "main",
"worktree_path": null,
"commit": null,
"pr_url": null,
"subtasks": [],
"children": [],
"parent": null,
"relatedFiles": [],
"notes": "",
"meta": {}
}