diff --git a/assets/layers/defibrillator/defibrillator.json b/assets/layers/defibrillator/defibrillator.json index 513960b7f4..2d266dd04d 100644 --- a/assets/layers/defibrillator/defibrillator.json +++ b/assets/layers/defibrillator/defibrillator.json @@ -690,37 +690,7 @@ ], "id": "defibrillator-survey:date" }, - { - "render": { - "en": "Extra information for OpenStreetMap experts: {fixme}", - "nl": "Extra informatie voor OpenStreetMap experts: {fixme}", - "fr": "Informations supplémentaires pour les experts d'OpenStreetMap : {fixme}", - "it": "Informazioni aggiuntive per gli esperti di OpenStreetMap: {fixme}", - "de": "Zusätzliche Informationen für OpenStreetMap-Experten: {fixme}", - "ru": "Дополнительная информация для экспертов OpenStreetMap: {fixme}", - "sl": "Dodatne informacije za OpenStreetMap strokovnjake: {fixme}", - "es": "Información adicional para expertos de OpenStreetMap: {fixme}", - "ca": "Informació addicional per als experts en OpenStreetMap: {fixme}", - "pl": "Więcej informacji dla doświadczonych użytkowników OpenStreetMap: {fixme}", - "cs": "Další informace pro experty OpenStreetMap: {fixme}" - }, - "question": { - "en": "Is there something wrong with how this is mapped, that you weren't able to fix here? (leave a note to OpenStreetMap experts)", - "nl": "Is er iets mis met de informatie over deze defibrillator dat je hier niet opgelost kreeg? (laat hier een berichtje achter voor OpenStreetMap experts)", - "fr": "Y a-t-il quelque chose qui ne va pas dans la manière dont ça a été cartographié, et que vous n'avez pas pu réparer ici ? (laisser une note pour les experts d'OpenStreetMap)", - "it": "C'è qualcosa di sbagliato nel modo in cui è mappato, che non sei riuscito a correggere qui? (lascia una nota agli esperti di OpenStreetMap)", - "de": "Gibt es einen Fehler in der Kartierung, den Sie hier nicht beheben konnten? (hinterlasse eine Notiz für OpenStreetMap-Experten)", - "sl": "Ali je kaj narobe s tem vnosom na zemljevid, in tega niste mogli sami popraviti tu? (pustite opombo OpenStreetMap strokovnjakom)", - "es": "¿Hay algo mal en cómo está mapeado esto, que no hayas podido arreglar aquí? (deja una nota para los expertos de OpenStreetMap)", - "ca": "Hi ha alguna cosa malament en la manera de com està mapejat això, que no heu pogut solucionar aquí? (deixeu una nota als experts d'OpenStreetMap)", - "cs": "Je na tom, jak je to zmapováno, něco v nepořádku, co jste zde nedokázali opravit? (zanechte poznámku odborníkům na OpenStreetMap)" - }, - "freeform": { - "key": "fixme", - "type": "text" - }, - "id": "defibrillator-fixme" - } + "fixme" ], "filter": [ "has_image", diff --git a/assets/layers/questions/questions.json b/assets/layers/questions/questions.json index b4cb97605e..45c979d3be 100644 --- a/assets/layers/questions/questions.json +++ b/assets/layers/questions/questions.json @@ -772,6 +772,36 @@ "cs": "Neopakujte již uvedená fakta" } }, + { + "render": { + "en": "Extra information for OpenStreetMap experts: {fixme}", + "nl": "Extra informatie voor OpenStreetMap experts: {fixme}", + "fr": "Informations supplémentaires pour les experts d'OpenStreetMap : {fixme}", + "it": "Informazioni aggiuntive per gli esperti di OpenStreetMap: {fixme}", + "de": "Zusätzliche Informationen für OpenStreetMap-Experten: {fixme}", + "ru": "Дополнительная информация для экспертов OpenStreetMap: {fixme}", + "sl": "Dodatne informacije za OpenStreetMap strokovnjake: {fixme}", + "es": "Información adicional para expertos de OpenStreetMap: {fixme}", + "ca": "Informació addicional per als experts en OpenStreetMap: {fixme}", + "pl": "Więcej informacji dla doświadczonych użytkowników OpenStreetMap: {fixme}", + "cs": "Další informace pro experty OpenStreetMap: {fixme}" + }, + "question": { + "en": "Is there something wrong with how this is mapped, that you weren't able to fix here? (leave a note to OpenStreetMap experts)", + "fr": "Y a-t-il quelque chose qui ne va pas dans la manière dont ça a été cartographié, et que vous n'avez pas pu réparer ici ? (laisser une note pour les experts d'OpenStreetMap)", + "it": "C'è qualcosa di sbagliato nel modo in cui è mappato, che non sei riuscito a correggere qui? (lascia una nota agli esperti di OpenStreetMap)", + "de": "Gibt es einen Fehler in der Kartierung, den Sie hier nicht beheben konnten? (hinterlasse eine Notiz für OpenStreetMap-Experten)", + "sl": "Ali je kaj narobe s tem vnosom na zemljevid, in tega niste mogli sami popraviti tu? (pustite opombo OpenStreetMap strokovnjakom)", + "es": "¿Hay algo mal en cómo está mapeado esto, que no hayas podido arreglar aquí? (deja una nota para los expertos de OpenStreetMap)", + "ca": "Hi ha alguna cosa malament en la manera de com està mapejat això, que no heu pogut solucionar aquí? (deixeu una nota als experts d'OpenStreetMap)", + "cs": "Je na tom, jak je to zmapováno, něco v nepořádku, co jste zde nedokázali opravit? (zanechte poznámku odborníkům na OpenStreetMap)" + }, + "freeform": { + "key": "fixme", + "type": "text" + }, + "id": "fixme" + }, { "id": "opening_hours", "question": { diff --git a/assets/layers/sauna/license_info.json b/assets/layers/sauna/license_info.json new file mode 100644 index 0000000000..9e41697de5 --- /dev/null +++ b/assets/layers/sauna/license_info.json @@ -0,0 +1,12 @@ +[ + { + "path": "sauna.svg", + "license": "CC0-1.0", + "authors": [ + "Geozeisig" + ], + "sources": [ + "https://wiki.openstreetmap.org/wiki/File:Sauna-14.svg" + ] + } +] \ No newline at end of file diff --git a/assets/layers/sauna/sauna.json b/assets/layers/sauna/sauna.json new file mode 100644 index 0000000000..23fedd0237 --- /dev/null +++ b/assets/layers/sauna/sauna.json @@ -0,0 +1,52 @@ +{ + "id": "sauna", + "name": { + "en": "Sauna" + }, + "description": { + "en": "A sauna is a small room or house designed as a place to experience dry or wet heat sessions, or an establishment with one or more of these and auxiliary facilities." + }, + "source": { + "osmTags": { + "and": [ + "leisure=sauna" + ] + } + }, + "minzoom": 8, + "title": { + "render": { + "en": "{name}" + } + }, + "pointRendering": [ + { + "location": [ + "point", + "centroid" + ], + "marker": [ + { + "icon": "./assets/layers/sauna/sauna.svg" + } + ] + } + ], + "lineRendering": [ + { + "width": 1, + "color": "blue" + } + ], + "tagRenderings": [ + "images", + "reviews", + "opening_hours", + "contact", + "sauna_at_leisure.sauna_expanded", + "fixme" + ], + "allowMove": true, + "credits": "Osmwithspace", + "credits:uid": 8770388 +} diff --git a/assets/layers/sauna/sauna.svg b/assets/layers/sauna/sauna.svg new file mode 100644 index 0000000000..49f43a322b --- /dev/null +++ b/assets/layers/sauna/sauna.svg @@ -0,0 +1,26 @@ + + + + + + + image/svg+xml + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/assets/layers/sauna/sauna.svg.license b/assets/layers/sauna/sauna.svg.license new file mode 100644 index 0000000000..5e3616ed7f --- /dev/null +++ b/assets/layers/sauna/sauna.svg.license @@ -0,0 +1,2 @@ +SPDX-FileCopyrightText: Geozeisig +SPDX-License-Identifier: CC0-1.0 \ No newline at end of file diff --git a/assets/layers/sauna_at_leisure/sauna_at_leisure.json b/assets/layers/sauna_at_leisure/sauna_at_leisure.json new file mode 100644 index 0000000000..e2f965c66f --- /dev/null +++ b/assets/layers/sauna_at_leisure/sauna_at_leisure.json @@ -0,0 +1,324 @@ +{ + "id": "sauna_at_leisure", + "name": { + "en": "Saunas at other amenities", + "de": "Saunen in anderen Einrichtungen" + }, + "description": { + "en": "A sauna is a small room or house designed as a place to experience dry or wet heat sessions, or an establishment with one or more of these and auxiliary facilities." + }, + "#": "Use 'sauna_at_leisure.sauna_grouped' in a layer.tagRenderings to add the 'sauna information' expandle block (incl 'has sauna'); use 'sauna_at_leisure.expanded' to get all sauna questions directly (which does _not_ include the 'has sauna' question)", + "source": { + "osmTags": { + "or": [ + "sauna=yes" + ] + } + }, + "minzoom": 8, + "title": { + "render": { + "en": "{name}" + } + }, + "pointRendering": [ + { + "location": [ + "point", + "centroid" + ], + "marker": [ + { + "icon": "./assets/layers/sauna/sauna.svg" + } + ] + } + ], + "lineRendering": [ + { + "width": 1, + "color": "blue" + } + ], + "tagRenderings": [ + { + "id": "sauna-group", + "labels": [ + "sauna_grouped" + ], + "render": { + "special": { + "type": "group", + "header": "sauna-header", + "labels": "has_sauna;sauna_expanded;sauna-questions" + } + } + }, + { + "id": "sauna-header", + "labels": [ + "sauna_grouped", + "hidden" + ], + "render": { + "en": "Sauna information" + }, + "icon": "./assets/layers/sauna/sauna.svg", + "mappings": [ + { + "if": "sauna=no", + "then": { + "en": "No sauna" + } + } + ] + }, + { + "id": "sauna-picture-carousel", + "labels": [ + "sauna_expanded", + "sauna_grouped", + "hidden" + ], + "render": { + "special": { + "type": "image_carousel", + "image_key": "sayna:panoramax;sauna:image;sauna:mapillary" + } + } + }, + { + "id": "sauna-picture", + "condition": { + "and": [ + { + "or": [ + "sauna=yes", + "leisure=sauna", + "beauty=sauna" + ] + } + ] + }, + "labels": [ + "sauna_expanded", + "sauna_grouped", + "hidden" + ], + "render": { + "special": { + "type": "image_upload", + "image_key": "sauna:panoramax", + "label": { + "en": "Add a picture of the sauna" + } + } + } + }, + { + "question": { + "en": "Does {title()} have a sauna?" + }, + "id": "has_sauna", + "labels": [ + "sauna_grouped", + "at_leisure_only", + "hidden" + ], + "mappings": [ + { + "if": "sauna=yes", + "then": { + "en": "Has a sauna" + } + }, + { + "if": "sauna=no", + "then": { + "en": "No sauna" + } + } + ] + }, + { + "id": "sauna_access", + "labels": [ + "sauna_expanded", + "sauna_grouped", + "hidden" + ], + "condition": { + "and": [ + { + "or": [ + "sauna=yes" + ] + } + ] + }, + "question": { + "en": "Is this sauna publicly accessible?", + "de": "Ist die Sauna öffentlich zugänglich?" + }, + "mappings": [ + { + "if": "sauna:access=yes", + "then": { + "en": "Public access", + "de": "Der Zugang ist öffentlich", + "fr": "Accès publique", + "nl": "Publiek toegankelijk", + "it": "Accesso pubblico", + "ru": "Свободный доступ", + "es": "Acceso público", + "da": "Offentlig adgang", + "ca": "Accés públic", + "cs": "Veřejný přístup", + "sl": "Javno dostopno" + } + }, + { + "if": "sauna:access=customers", + "then": { + "en": "Only access to customers of the amenity", + "de": "Nur Zugang für Kunden der Einrichtung", + "nl": "Enkel toegankelijk voor klanten van de voorziening", + "fr": "Accessibles uniquement au clients du lieu", + "ca": "Només accessible a clients de l'instal·lació", + "cs": "Přístup pouze zákazníkům zařízení občanské vybavenosti", + "sl": "Samo za stranke lokala", + "es": "Solo acceso para clientes del servicio" + } + }, + { + "if": "sauna:access=no", + "then": { + "en": "Not accessible, even for customers of the amenity", + "de": "Nicht zugänglich, auch nicht für Kunden der Einrichtung", + "nl": "Niet toegankelijk, ook niet voor klanten van de voorziening", + "fr": "Non accessibles, même pour les clients du lieu", + "ca": "No accessible, inclús per als clients de la instal·lació", + "cs": "Není přístupný, a to ani pro zákazníky občanské vybavenosti", + "sl": "Ni dostopno niti za stranke lokala", + "es": "Inaccesible, incluso para clientes del servicio" + } + }, + { + "if": "sauna:access=public", + "then": { + "en": "Public access", + "de": "Öffentlicher Zugang", + "fr": "Accès publique", + "nl": "Publiek toegankelijk", + "it": "Accesso pubblico", + "ru": "Свободный доступ", + "es": "Acceso público", + "da": "Offentlig adgang", + "ca": "Accés públic", + "cs": "Veřejný přístup" + }, + "hideInAnswer": true + } + ] + }, + { + "id": "charge_cost_rewritten", + "rewrite": { + "sourceString": [ + "{key}", + "{time}" + ], + "into": [ + [ + "2 hours", + { + "en": "2 hours", + "de": "2 Stunden" + } + ], + [ + "4 hours", + { + "en": "4 hours", + "de": "4 Stunden" + } + ], + [ + "day", + { + "en": "one day", + "de": "einen Tag" + } + ] + ] + }, + "renderings": [ + { + "id": "charge_{key}", + "labels": [ + "sauna_expanded", + "sauna_grouped", + "hidden" + ], + "question": { + "en": "What is the entrance fee for {time}?", + "de": "Was ist der Eintrittspreis für {time}?" + }, + "render": { + "en": "entrance fee for {time}: {charge}", + "de": "Eintrittspreis für {time}: {charge}" + }, + "freeform": { + "key": "charge", + "type": "currency", + "inline": true, + "postfixDistinguished": "{key}", + "addExtraTags": [ + "fee=yes" + ] + }, + "mappings": [ + { + "if": "fee=no", + "addExtraTags": [ + "charge=" + ], + "then": { + "en": "The sauna is free of charge", + "de": "Die Sauna ist kostenlos" + } + } + ], + "condition": { + "and": [ + "access!=customers", + "access!=no", + "access!=private", + { + "or": [ + "sauna=yes" + ] + } + ] + } + } + ] + }, + { + "id": "sauna-questions", + "labels": [ + "sauna_grouped", + "hidden" + ], + "render": { + "special": { + "type": "questions", + "labels": "at_leisure_only;sauna_expanded" + } + } + } + ], + "allowMove": true, + "credits": "Osmwithspace", + "credits:uid": 8770388 +} diff --git a/assets/layers/shops/shops.json b/assets/layers/shops/shops.json index cceec48e18..e66da0144b 100644 --- a/assets/layers/shops/shops.json +++ b/assets/layers/shops/shops.json @@ -365,6 +365,69 @@ "filter": true } }, + { + "id": "beauty_shop_type", + "question": { + "en": "What type of beauty shop is this?" + }, + "multiAnswer": true, + "mappings": [ + { + "if": "beauty=nails", + "then": { + "en": "Offers nail care services such as manicures, pedicures, and nail enhancements" + } + }, + { + "if": "beauty=skin_care", + "then": { + "en": "Offers skin care services" + } + }, + { + "if": "beauty=tanning", + "then": { + "en": "Offers tanning services such as sunbeds" + } + }, + { + "if": "beauty=cosmetics", + "then": { + "en": "Offers cosmetic services, such as makeup" + } + }, + { + "if": "beauty=massage", + "then": { + "en": "Offers massages" + } + }, + { + "if": "beauty=waxing", + "then": { + "en": "Offers hair removal through waxing" + } + }, + { + "if": "beauty=hair_removal", + "then": { + "en": "Offers hair removal services, e.g. with a laser" + } + }, + { + "if": "beauty=eyebrow", + "then": { + "en": "Offers eyebrow enhancement services" + } + }, + { + "if": "beauty=pedicure", + "then": { + "en": "Offers pedicure services" + } + } + ] + }, { "id": "brand", "question": { @@ -1357,9 +1420,7 @@ { "builtin": "bike_cleaning.bike_cleaning-service_bicycle_cleaning_charge" }, - "internet", - "internet-fee", - "internet-ssid", + "internet-all", { "id": "organic", "question": { @@ -1471,6 +1532,21 @@ } } }, + { + "builtin": "sauna_at_leisure.sauna_grouped", + "override": { + "condition": { + "and+": [ + { + "or": [ + "shop=beauty", + "shop=massage" + ] + } + ] + } + } + }, "description", "toilet_at_amenity_lib.all" ], diff --git a/assets/layers/sports_centre/sports_centre.json b/assets/layers/sports_centre/sports_centre.json index 6d59fc0ec0..795ec5d5e5 100644 --- a/assets/layers/sports_centre/sports_centre.json +++ b/assets/layers/sports_centre/sports_centre.json @@ -1446,7 +1446,8 @@ "it": "Quali sport si praticano in questa struttura?", "cs": "Jaké sporty se provozují na tomto sportovišti?" } - } + }, + "sauna_at_leisure.sauna_grouped" ], "filter": [ "open_now" diff --git a/assets/layers/tourism_accomodation/tourism_accomodation.json b/assets/layers/tourism_accomodation/tourism_accomodation.json index 75885933f9..7e32981e39 100644 --- a/assets/layers/tourism_accomodation/tourism_accomodation.json +++ b/assets/layers/tourism_accomodation/tourism_accomodation.json @@ -408,6 +408,7 @@ "contact", "wheelchair-access", "toilet_at_amenity_lib.all", + "sauna_at_leisure.sauna_grouped", "internet-all", "dog-access" ], diff --git a/assets/themes/sauna/sauna.json b/assets/themes/sauna/sauna.json new file mode 100644 index 0000000000..0f45cb7eec --- /dev/null +++ b/assets/themes/sauna/sauna.json @@ -0,0 +1,135 @@ +{ + "id": "sauna", + "title": { + "en": "Sauna" + }, + "description": { + "en": "Sauna" + }, + "icon": "./assets/layers/sauna/sauna.svg", + "credits": [ + "Osmwithspace" + ], + "#layers": "sauna_at_leisure acts as fallback-layer and will show all objects with `sauna=yes`", + "layers": [ + "sauna", + { + "builtin": "tourism_accomodation", + "override": { + "id": "tourism_accomodation_with_sauna", + "presets=": [], + "filter=": [], + "minzoom": 8, + "source": { + "osmTags": { + "and+": "sauna=yes" + } + } + } + }, + { + "builtin": "tourism_accomodation", + "override": { + "minzoom": 18, + "name=": null, + "filter": { + "sameAs": "tourism_accomodation_with_sauna" + } + } + }, + { + "builtin": "sports_centre", + "override": { + "minzoom": 8, + "id": "sports_centre_with_sauna", + "presets=": [], + "filter=":[], + "source": { + "osmTags": { + "and+": [ + "sauna=yes" + ] + } + } + } + }, + { + "builtin": "sports_centre", + "override": { + "name": null, + "minzoom": 18, + "filter": { + "sameAs": "sports_centre_with_sauna" + } + } + }, + { + "builtin": "shops", + "override": { + "id": "shops_with_sauna", + "source": { + "osmTags": + { + "and+": [ + "sauna=yes" + ] + } + + }, + "presets=":[], + "minzoom": 8, + "filter=": [] + } + }, + { + "builtin": "shops", + "hideTagRenderingsWithLabels": [ + "shop_types" + ], + "override": { + "id": "beauty_shops", + "minzoom": 18, + "name=": null, + "source": { + "osmTags": { + "and+": [ + { + "or": [ + "shop=beauty", + "shop=massage" + ] + } + ] + } + }, + "presets=": [ + { + "tags": [ + "shop=beauty" + ], + "title": { + "en": "a beauty shop" + } + }, + { + "tags": [ + "shop=massage" + ], + "title": { + "en": "a massage shop" + } + } + ] + } + }, + { + "builtin": "toilet", + "override": { + "minzoom":18, + "name=": null + } + }, + "sauna_at_leisure" + ], + "credits:uid": 8770388 +} diff --git a/src/Models/ThemeConfig/Conversion/AddPrefixToTagRenderingConfig.ts b/src/Models/ThemeConfig/Conversion/AddPrefixToTagRenderingConfig.ts index 5feb391f7c..176b39459f 100644 --- a/src/Models/ThemeConfig/Conversion/AddPrefixToTagRenderingConfig.ts +++ b/src/Models/ThemeConfig/Conversion/AddPrefixToTagRenderingConfig.ts @@ -6,6 +6,7 @@ import { MappingConfigJson, QuestionableTagRenderingConfigJson, } from "../Json/QuestionableTagRenderingConfigJson" +import { Utils } from "../../../Utils" export default class AddPrefixToTagRenderingConfig extends DesugaringStep { private readonly _prefix: string @@ -18,6 +19,40 @@ export default class AddPrefixToTagRenderingConfig extends DesugaringStep "Some argument with a {PREFIX:key}" + * + * // Don't rewrite metatags + * new AddPrefixToTagRenderingConfig("PREFIX").rewriteArguments("Some argument with a {_calculated_key}") // => "Some argument with a {_calculated_key}" + * + + */ + private rewriteArguments(txt: string) { + const regex = /(.*?){([^}]*)}(.*)/s + let match = txt.match(regex) + if (!match) { + return txt + } + let result = "" + while (match) { + const [_, normal, key, leftover] = match + if (key.startsWith("_")) { + result += normal + "{" + key + "}" + } else { + result += normal + "{" + this._prefix + ":" + key + "}" + } + match = leftover.match(regex) + if (!match) { + result += leftover + } + } + if(txt !== result){ + console.log(">>> Rewritten", txt, "into", result) + } + return result + } + /** * * const edit = new AddPrefixToTagRenderingConfig("PREFIX") @@ -29,6 +64,9 @@ export default class AddPrefixToTagRenderingConfig extends DesugaringStep "{opening_hours_table(PREFIX:opening_hours,,)}" + * + * // Should prefix links, e.g. for 'phone' + * new AddPrefixToTagRenderingConfig("PREFIX").updateString("{link({phone},tel:{phone},,,,)}") // => "{link({PREFIX:phone},tel:{PREFIX:phone},,,,)}" */ private updateString(str: string): string { const parsed = SpecialVisualizations.constructSpecification(str) @@ -45,7 +83,7 @@ export default class AddPrefixToTagRenderingConfig extends DesugaringStep { return json } - json.source = { osmTags } + json.source = { osmTags: {and: [osmTags]} } return json } } diff --git a/src/Models/ThemeConfig/Conversion/PrepareTheme.ts b/src/Models/ThemeConfig/Conversion/PrepareTheme.ts index bbf154fc99..68848a055d 100644 --- a/src/Models/ThemeConfig/Conversion/PrepareTheme.ts +++ b/src/Models/ThemeConfig/Conversion/PrepareTheme.ts @@ -506,7 +506,11 @@ class WarnForUnsubstitutedLayersInTheme extends DesugaringStep if (layer["builtin"] !== undefined) { continue } - if (layer["source"]["geojson"] !== undefined) { + if(layer["override"]!==undefined){ + context.err("Got an `override` block without a `builtin`-specification") + continue + } + if (layer["source"]?.["geojson"] !== undefined) { // We turn a blind eye for import layers continue } diff --git a/src/Models/ThemeConfig/LayerConfig.ts b/src/Models/ThemeConfig/LayerConfig.ts index d270044586..db66b509e7 100644 --- a/src/Models/ThemeConfig/LayerConfig.ts +++ b/src/Models/ThemeConfig/LayerConfig.ts @@ -71,7 +71,7 @@ export default class LayerConfig extends WithContextLoader { * If this layer is based on another layer, this might be indicated here * @private */ - private readonly _basedOn: string | undefined + public readonly _basedOn: string | undefined constructor( json: LayerConfigJson, diff --git a/src/UI/Popup/DataVisualisations.ts b/src/UI/Popup/DataVisualisations.ts index d1b5a885fd..05b15f4710 100644 --- a/src/UI/Popup/DataVisualisations.ts +++ b/src/UI/Popup/DataVisualisations.ts @@ -248,6 +248,10 @@ class PresetTypeSelect extends SpecialVisualizationSvelte { layer: LayerConfig, ): SvelteUIElement { const t = Translations.t.preset_type + if(layer._basedOn !== layer.id){ + console.warn("Trying to use the _original_ layer") + layer = state.theme.layers.find(l => l.id === layer._basedOn) ?? layer + } const question: QuestionableTagRenderingConfigJson = { id: layer.id + "-type", question: t.question.translations, @@ -260,6 +264,10 @@ class PresetTypeSelect extends SpecialVisualizationSvelte { }).translations, })), } + if(question.mappings.length === 0){ + console.error("No mappings for preset_type_select, something went wrong") + return undefined + } const config = new TagRenderingConfig(question) return new SvelteUIElement(TagRenderingEditable, { config,