Add --theme option to select 3DCityDB v5 textures by appearance theme - #259
Add --theme option to select 3DCityDB v5 textures by appearance theme#259christianbraun wants to merge 6 commits into
Conversation
3DCityDB v5+ can hold many appearance themes per shared geometry. The texture-enrichment query previously joined surface_data_mapping -> surface_data -> tex_image with no appearance filter, so a geometry with multiple mappings always rendered the lowest surface_data_id. Add an optional --theme option that, when set, joins appear_to_surface_data + appearance and filters on appearance.theme, letting one shared geometry serve N themes via N runs (no geometry duplication). Empty theme keeps the original behaviour.
A surface_data can be referenced by multiple appearance rows sharing the same theme string; the previous fan-out JOIN then emitted N identical rows per surface, and EnrichWithTextures adds each without dedup, embedding the same image N times. Replace the appearance JOIN with an EXISTS semi-join so each matching surface_data contributes exactly one row. Empty theme still reproduces the original query verbatim.
|
Related issue: #252 |
Adds a 3DCityDB v5 appearance fixture (citydb.appearance / citydb.appear_to_surface_data, column names taken from a real v5 database) and a fourth geometry whose single surface is textured twice - red under theme 'summer', blue under 'winter'. Selecting 'winter' must return the blue texture, which the unfiltered query would never pick (lower surface_data_id wins). 'summer' is carried by two appearances that both reference the same surface_data, so the second test pins the EXISTS semi-join: one texture, not one per appearance. The fixture is a separate script and sits outside the bounding boxes the existing texture tests query, so their expectations are untouched.
|
Hi, looks good this addition, can you add the new parameter to README.md and a description to dataprocessing/dataprocessing_citygml.md |
|
Hi, you're welcome. I made the additions. |
--theme " " fell through the string.Empty check and filtered on a theme no appearance carries, silently dropping every texture. IsNullOrWhiteSpace makes blank mean absent, which is what the option's default documents. Also moves the test helpers to the top of the class and corrects a comment that said the unfiltered query picks the lowest surface_data_id - it returns both mappings, and the renderer takes the first per objectId.
A theme nobody wrote is not an error to the tiler: it bakes a complete, valid tileset in which every tile is untextured, with the same exit code and tile count, so a typo only surfaces in the viewer. Probe citydb.appearance once, up front, and warn. Not per tile - with a theme filter most tiles are legitimately untextured. Gated on the texture pipeline, since citydb.appearance need not exist otherwise.
|
Do you have a link to a Luxemburg textured building CityGML dataset (with multiple appearances)? |
maybe https://data.public.lu/en/datasets/base-de-donnees-nationale-des-batiments-3d-2023/ update: ACT2023v2_bati3d_Beaufort.gml only has 1 appearance texture |
that's the base data I am working with. This has one appearance theme. I am about to calculate others. When I am ready to share I will provide a demo data set. |
What
Adds an optional
--theme <name>flag to the 3DCityDB v5+ texture pipeline. When set, only textures belonging to that appearance theme are exported.Why
3DCityDB v5 can hold many appearance themes over one shared geometry (e.g. an aerial photo theme plus per-period analysis themes), each theme being a set of
appearancerows that referencesurface_dataviaappear_to_surface_data.Today the texture-enrichment query joins
geometry_data -> surface_data_mapping -> surface_data -> tex_imagewith no appearance filter andORDER BY g.id, sdm.surface_data_id, so a geometry with multiple mappings always renders the lowestsurface_data_idand silently ignores every other theme. There is no way to ask for a specific theme.This matters for use cases where one building geometry carries several textured "layers" (analysis results, thematic overlays) and you want to publish one tileset per theme from a single shared geometry, rather than duplicating geometry per theme.
How
--themeoption (Options.cs), default empty. Threaded throughInputTable-> both tilers ->GetGeometrySubset->EnrichWithTextures, mirroring the existing plumbing forIdColumn/Query.EnrichWithTexturesadds anEXISTSsemi-join onappear_to_surface_data+appearancefilteringappearance.theme = @theme. A semi-join (not a plain JOIN) is used so asurface_datareferenced by multiple appearances sharing the theme still yields exactly one row, never duplicate embedded textures.@theme) - no string interpolation of user input.Backwards compatibility
Testing
Verified on a 3DCityDB v5.0 database (Luxembourg 3D open-data) where
geometry_dataid=1 carries two mappings: a photo texture (themeAerial, lowersurface_data_id) and a hand-authored analysis texture (themetest).--theme: exported glb embeds the photo JPEG (39066 B) - unchanged baseline.--theme test: exported glb embeds the analysis PNG (393 B), a single texture, no duplication.