From 8d670a56603960b28506756426f8902d9001468d Mon Sep 17 00:00:00 2001 From: mcliquid Date: Mon, 20 Nov 2023 20:03:35 +0100 Subject: [PATCH 01/15] First modifications of the recycling quest --- .../guidepost_sport/AddGuidepostSports.kt | 143 ++++++++++++++++++ .../guidepost_sport/AddGuidepostSportsForm.kt | 66 ++++++++ .../quests/guidepost_sport/GuidepostSport.kt | 20 +++ .../guidepost_sport/GuidepostSportsAnswer.kt | 6 + .../guidepost_sport/GuidepostSporttem.kt | 47 ++++++ app/src/main/res/values/strings_ee.xml | 13 ++ 6 files changed, 295 insertions(+) create mode 100644 app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt create mode 100644 app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt create mode 100644 app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSport.kt create mode 100644 app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt create mode 100644 app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt new file mode 100644 index 00000000000..35df60ad2be --- /dev/null +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt @@ -0,0 +1,143 @@ +package de.westnordost.streetcomplete.quests.guidepost_sport + +import de.westnordost.streetcomplete.R +import de.westnordost.streetcomplete.data.elementfilter.filters.RelativeDate +import de.westnordost.streetcomplete.data.elementfilter.filters.TagOlderThan +import de.westnordost.streetcomplete.data.elementfilter.toElementFilterExpression +import de.westnordost.streetcomplete.data.osm.geometry.ElementGeometry +import de.westnordost.streetcomplete.data.osm.mapdata.Element +import de.westnordost.streetcomplete.data.osm.mapdata.MapDataWithGeometry +import de.westnordost.streetcomplete.data.osm.mapdata.filter +import de.westnordost.streetcomplete.data.osm.osmquests.OsmElementQuestType +import de.westnordost.streetcomplete.data.user.achievements.EditTypeAchievement.CITIZEN +import de.westnordost.streetcomplete.osm.Tags +import de.westnordost.streetcomplete.osm.hasCheckDateForKey +import de.westnordost.streetcomplete.osm.removeCheckDatesForKey +import de.westnordost.streetcomplete.osm.updateCheckDateForKey +import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.BEVERAGE_CARTONS +import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.PET +import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.PLASTIC_BOTTLES +import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.PLASTIC_PACKAGING + +class AddGuidepostSports : OsmElementQuestType { + + private val filter by lazy { """ + nodes with + tourism = information + and information ~ guidepost|route_marker + and !hiking and !bicycle and !mtb and !climbing and !horse and !nordic_walking and !ski and !inline_skates and !running + and !disused + and !guidepost + """.toElementFilterExpression() } + + override val changesetComment = "Specify what can be recycled in recycling containers" + override val wikiLink = "Tag:information=guidepost" + override val icon = R.drawable.ic_quest_recycling_container + override val isDeleteElementEnabled = true + override val defaultDisabledMessage = R.string.default_disabled_msg_seasonal + + override fun getTitle(tags: Map) = R.string.quest_guidepost_sports_title + + override fun getApplicableElements(mapData: MapDataWithGeometry): Iterable = + mapData.nodes.filter { isApplicableTo(it) } + + override fun isApplicableTo(element: Element): Boolean = + /* Only recycling containers that do either not have any recycling:* tag yet or + * haven't been touched for 2 years and are exclusively recycling types selectable in + * StreetComplete. */ + filter.matches(element) && ( + !element.hasAnyRecyclingMaterials() + || recyclingOlderThan2Years.matches(element) && !element.hasUnknownRecyclingMaterials() + ) + + override fun createForm() = AddGuidepostSportsForm() + + override fun getHighlightedElements(element: Element, getMapData: () -> MapDataWithGeometry) = + getMapData().filter("nodes with tourism = information and information ~ guidepost|route_marker") + + override fun applyAnswerTo(answer: RecyclingContainerMaterialsAnswer, tags: Tags, geometry: ElementGeometry, timestampEdited: Long) { + if (answer is RecyclingMaterials) { + applyRecyclingMaterialsAnswer(answer.materials, tags) + } else if (answer is IsWasteContainer) { + applyWasteContainerAnswer(tags) + } + } + + private fun applyRecyclingMaterialsAnswer(materials: List, tags: Tags) { + // first clear recycling:* taggings previously "yes" + for ((key, value) in tags.entries) { + if (key.startsWith("recycling:") && value == "yes") { + tags.remove(key) + } + } + + // if the user chose deliberately not "all plastic", also tag it explicitly + if (materials.any { it in RecyclingMaterial.plastics }) { + for (plastic in RecyclingMaterial.plastics) { + tags.remove("recycling:${plastic.value}") + } + when { + PLASTIC_PACKAGING in materials -> { + tags["recycling:plastic"] = "no" + } + BEVERAGE_CARTONS in materials && PLASTIC_BOTTLES in materials -> { + tags["recycling:plastic_packaging"] = "no" + tags["recycling:plastic"] = "no" + } + BEVERAGE_CARTONS in materials -> { + tags["recycling:plastic_bottles"] = "no" + tags["recycling:plastic_packaging"] = "no" + tags["recycling:plastic"] = "no" + } + PLASTIC_BOTTLES in materials -> { + tags["recycling:beverage_cartons"] = "no" + tags["recycling:plastic_packaging"] = "no" + tags["recycling:plastic"] = "no" + } + PET in materials -> { + tags["recycling:plastic_bottles"] = "no" + tags["recycling:beverage_cartons"] = "no" + tags["recycling:plastic_packaging"] = "no" + tags["recycling:plastic"] = "no" + } + } + } + + // set selected recycling:* taggings to "yes" + val selectedMaterials = materials.map { "recycling:${it.value}" } + for (material in selectedMaterials) { + tags[material] = "yes" + } + + // only set the check date if nothing was changed + if (!tags.hasChanges || tags.hasCheckDateForKey("recycling")) { + tags.updateCheckDateForKey("recycling") + } + } + + private fun applyWasteContainerAnswer(tags: Tags) { + tags["amenity"] = "waste_disposal" + tags.remove("recycling_type") + + val recyclingKeys = tags.keys.filter { it.startsWith("recycling:") } + for (key in recyclingKeys) { + tags.remove(key) + } + tags.removeCheckDatesForKey("recycling") + } +} + +private val recyclingOlderThan2Years = + TagOlderThan("recycling", RelativeDate(-(365 * 2).toFloat())) + +private val allKnownMaterials = GuidepostSport.values().map { "recycling:" + it.value } + +private fun Element.hasAnyRecyclingMaterials(): Boolean = + tags.any { it.key.startsWith("recycling:") && it.value == "yes" } + +private fun Element.hasUnknownRecyclingMaterials(): Boolean = + tags.any { + it.key.startsWith("recycling:") + && it.key !in allKnownMaterials + && it.value == "yes" + } diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt new file mode 100644 index 00000000000..3302f4d0c5d --- /dev/null +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt @@ -0,0 +1,66 @@ +package de.westnordost.streetcomplete.quests.guidepost_sport + +import android.os.Bundle +import androidx.appcompat.app.AlertDialog +import de.westnordost.streetcomplete.R +import de.westnordost.streetcomplete.quests.AImageListQuestForm +import de.westnordost.streetcomplete.quests.AnswerItem +import de.westnordost.streetcomplete.view.image_select.ImageListPickerDialog +import de.westnordost.streetcomplete.view.image_select.ImageSelectAdapter +import de.westnordost.streetcomplete.view.image_select.Item + +class AddGuidepostSportsForm : + AImageListQuestForm, RecyclingContainerMaterialsAnswer>() { + + override val descriptionResId = R.string.quest_recycling_materials_note + + override val otherAnswers = listOf( + AnswerItem(R.string.quest_recycling_materials_answer_waste) { confirmJustTrash() } + ) + + override val items get() = GuidepostSport.selectableValues.map { it.asItem() } + + override val maxSelectableItems = -1 + + private val isAnyGlassRecycleable get() = countryInfo.isUsuallyAnyGlassRecyclableInContainers + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + imageSelector.cellLayoutId = R.layout.cell_icon_select_with_label_below + imageSelector.listeners.add(object : ImageSelectAdapter.OnItemSelectionListener { + override fun onIndexSelected(index: Int) { + val value = imageSelector.items[index].value!! + + if (value in GuidepostSport.selectableGuidepostValues) { + showPickItemForItemAtIndexDialog(index, GuidepostSport.selectablePlasticValues.map { it.asItem() }) + } else if (isAnyGlassRecycleable && value in GuidepostSport.selectableGlassValues) { + showPickItemForItemAtIndexDialog(index, GuidepostSport.selectableGlassValues.map { it.asItem() }) + } + } + + override fun onIndexDeselected(index: Int) {} + }) + } + + private fun showPickItemForItemAtIndexDialog(index: Int, items: List>>) { + val ctx = context ?: return + ImageListPickerDialog(ctx, items, R.layout.cell_icon_select_with_label_below, 3) { selected -> + val newList = imageSelector.items.toMutableList() + newList[index] = selected + imageSelector.items = newList + }.show() + } + + override fun onClickOk(selectedItems: List>) { + applyAnswer(RecyclingMaterials(selectedItems.flatten())) + } + + private fun confirmJustTrash() { + activity?.let { AlertDialog.Builder(it) + .setMessage(R.string.quest_recycling_materials_answer_waste_description) + .setPositiveButton(R.string.quest_generic_confirmation_yes) { _, _ -> applyAnswer(IsWasteContainer) } + .setNegativeButton(R.string.quest_generic_confirmation_no, null) + .show() + } + } +} diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSport.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSport.kt new file mode 100644 index 00000000000..cc987e5cd66 --- /dev/null +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSport.kt @@ -0,0 +1,20 @@ +package de.westnordost.streetcomplete.quests.guidepost_sport + +enum class GuidepostSport(val key: String) { + HIKING("hiking"), + BICYCLE("bicycle"), + MTB("mtb"), + CLIMBING("climbing"), + HORSE("horse"), + NORDIC_WALKING("nordic_walking"), + SKI("ski"), + INLINE_SKATING("inline_skating"), + RUNNING("running"), + WINTER_HIKING("winter_hiking"); + + companion object { + val selectableValues = listOf( + HIKING, BICYCLE, MTB, CLIMBING, HORSE, NORDIC_WALKING, SKI, INLINE_SKATING, RUNNING, WINTER_HIKING + ) + } +} diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt new file mode 100644 index 00000000000..c97ea81346e --- /dev/null +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt @@ -0,0 +1,6 @@ +package de.westnordost.streetcomplete.quests.guidepost_sport + +sealed interface RecyclingContainerMaterialsAnswer + +object IsWasteContainer : RecyclingContainerMaterialsAnswer +data class RecyclingMaterials(val materials: List) : RecyclingContainerMaterialsAnswer diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt new file mode 100644 index 00000000000..59d48edc631 --- /dev/null +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt @@ -0,0 +1,47 @@ +package de.westnordost.streetcomplete.quests.guidepost_sport + +import de.westnordost.streetcomplete.R +import de.westnordost.streetcomplete.quests.guidepost_sport.GuidepostSport.* +import de.westnordost.streetcomplete.view.image_select.Item + +fun GuidepostSport.asItem(): Item> = + Item(listOf(this), iconResId, titleResId) + +fun List.asItem(): Item> = + Item(this, iconResId, titleResId) + +private val GuidepostSport.iconResId: Int get() = when (this) { + HIKING -> R.drawable.ic_recycling_glass_bottles + BICYCLE -> R.drawable.ic_recycling_glass + MTB -> R.drawable.ic_recycling_paper + CLIMBING -> R.drawable.ic_recycling_plastic + HORSE -> R.drawable.ic_recycling_plastic_packaging + NORDIC_WALKING -> R.drawable.ic_recycling_plastic_bottles + SKI -> R.drawable.ic_recycling_pet + INLINE_SKATING -> R.drawable.ic_recycling_beverage_cartons + RUNNING -> R.drawable.ic_recycling_cans + WINTER_HIKING -> R.drawable.ic_recycling_cans +} + +private val GuidepostSport.titleResId: Int get() = when (this) { + HIKING -> R.string.quest_guidepost_sports_hiking + BICYCLE -> R.string.quest_guidepost_sports_bicycle + MTB -> R.string.quest_guidepost_sports_mtb + CLIMBING -> R.string.quest_guidepost_sports_climbing + HORSE -> R.string.quest_guidepost_sports_horse + NORDIC_WALKING -> R.string.quest_guidepost_sports_nordic_walking + SKI -> R.string.quest_guidepost_sports_ski + INLINE_SKATING -> R.string.quest_guidepost_sports_inline_skating + RUNNING -> R.string.quest_guidepost_sports_running + WINTER_HIKING -> R.string.quest_guidepost_sports_winter_hiking +} + +private val List.iconResId: Int get() = when (this) { + listOf(HIKING, BICYCLE) -> R.drawable.ic_recycling_plastic_bottles_and_cartons + else -> first().iconResId +} + +private val List.titleResId: Int get() = when (this) { + listOf(HIKING, BICYCLE) -> R.string.quest_recycling_type_plastic_bottles_and_cartons + else -> first().titleResId +} diff --git a/app/src/main/res/values/strings_ee.xml b/app/src/main/res/values/strings_ee.xml index 2ed05d004a1..bbe7690330e 100644 --- a/app/src/main/res/values/strings_ee.xml +++ b/app/src/main/res/values/strings_ee.xml @@ -259,6 +259,19 @@ Stone Bricks + + For which sport is this guidepost intended? + Hiking + Bicycle + MTB + Climbing + Horse + Nordic Walking + Ski + Inline Skating + Running + Winter Hiking + Is this pharmacy dispensing all prescription drugs? From 7530eba94df720a4cc8fae1931b5b05843e3f9e2 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Mon, 20 Nov 2023 20:05:53 +0100 Subject: [PATCH 02/15] remove unused imports --- .../quests/guidepost_sport/AddGuidepostSports.kt | 5 ----- 1 file changed, 5 deletions(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt index 35df60ad2be..19fdf18ee95 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt @@ -9,15 +9,10 @@ import de.westnordost.streetcomplete.data.osm.mapdata.Element import de.westnordost.streetcomplete.data.osm.mapdata.MapDataWithGeometry import de.westnordost.streetcomplete.data.osm.mapdata.filter import de.westnordost.streetcomplete.data.osm.osmquests.OsmElementQuestType -import de.westnordost.streetcomplete.data.user.achievements.EditTypeAchievement.CITIZEN import de.westnordost.streetcomplete.osm.Tags import de.westnordost.streetcomplete.osm.hasCheckDateForKey import de.westnordost.streetcomplete.osm.removeCheckDatesForKey import de.westnordost.streetcomplete.osm.updateCheckDateForKey -import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.BEVERAGE_CARTONS -import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.PET -import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.PLASTIC_BOTTLES -import de.westnordost.streetcomplete.quests.recycling_material.GuidepostSport.PLASTIC_PACKAGING class AddGuidepostSports : OsmElementQuestType { From f650966dbe16648bc341da1f6c2d4cf8af7c0443 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Fri, 22 Dec 2023 08:52:10 +0100 Subject: [PATCH 03/15] Added guidepost quest icons for activity selection --- .../guidepost_sport/GuidepostSporttem.kt | 20 +- .../res/drawable/ic_guidepost_climbing.xml | 108 +++++++++ .../res/drawable/ic_guidepost_cycling.xml | 123 ++++++++++ .../main/res/drawable/ic_guidepost_hiking.xml | 69 ++++++ .../drawable/ic_guidepost_horse_riding.xml | 222 ++++++++++++++++++ .../drawable/ic_guidepost_inline_skating.xml | 172 ++++++++++++++ .../main/res/drawable/ic_guidepost_mtb.xml | 54 +++++ .../drawable/ic_guidepost_nordic_walking.xml | 57 +++++ .../res/drawable/ic_guidepost_running.xml | 96 ++++++++ .../main/res/drawable/ic_guidepost_ski.xml | 69 ++++++ .../ic_guidepost_snow_shoe_hiking.xml | 115 +++++++++ res/graphics/guidepost/climbing.svg | 95 ++++++++ res/graphics/guidepost/cycling.svg | 81 +++++++ res/graphics/guidepost/hiking.svg | 54 +++++ res/graphics/guidepost/horse_riding.svg | 167 +++++++++++++ res/graphics/guidepost/inline_skating.svg | 120 ++++++++++ res/graphics/guidepost/mtb.svg | 52 ++++ res/graphics/guidepost/nordic_walking.svg | 96 ++++++++ res/graphics/guidepost/running.svg | 111 +++++++++ res/graphics/guidepost/ski.svg | 55 +++++ res/graphics/guidepost/snow_shoe_hiking.svg | 97 ++++++++ 21 files changed, 2023 insertions(+), 10 deletions(-) create mode 100644 app/src/main/res/drawable/ic_guidepost_climbing.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_cycling.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_hiking.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_horse_riding.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_inline_skating.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_mtb.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_nordic_walking.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_running.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_ski.xml create mode 100644 app/src/main/res/drawable/ic_guidepost_snow_shoe_hiking.xml create mode 100644 res/graphics/guidepost/climbing.svg create mode 100644 res/graphics/guidepost/cycling.svg create mode 100644 res/graphics/guidepost/hiking.svg create mode 100644 res/graphics/guidepost/horse_riding.svg create mode 100644 res/graphics/guidepost/inline_skating.svg create mode 100644 res/graphics/guidepost/mtb.svg create mode 100644 res/graphics/guidepost/nordic_walking.svg create mode 100644 res/graphics/guidepost/running.svg create mode 100644 res/graphics/guidepost/ski.svg create mode 100644 res/graphics/guidepost/snow_shoe_hiking.svg diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt index 59d48edc631..67de3cb7ceb 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt @@ -11,16 +11,16 @@ fun List.asItem(): Item> = Item(this, iconResId, titleResId) private val GuidepostSport.iconResId: Int get() = when (this) { - HIKING -> R.drawable.ic_recycling_glass_bottles - BICYCLE -> R.drawable.ic_recycling_glass - MTB -> R.drawable.ic_recycling_paper - CLIMBING -> R.drawable.ic_recycling_plastic - HORSE -> R.drawable.ic_recycling_plastic_packaging - NORDIC_WALKING -> R.drawable.ic_recycling_plastic_bottles - SKI -> R.drawable.ic_recycling_pet - INLINE_SKATING -> R.drawable.ic_recycling_beverage_cartons - RUNNING -> R.drawable.ic_recycling_cans - WINTER_HIKING -> R.drawable.ic_recycling_cans + HIKING -> R.drawable.ic_guidepost_hiking + BICYCLE -> R.drawable.ic_guidepost_cycling + MTB -> R.drawable.ic_guidepost_mtb + CLIMBING -> R.drawable.ic_guidepost_climbing + HORSE -> R.drawable.ic_guidepost_horse_riding + NORDIC_WALKING -> R.drawable.ic_guidepost_nordic_walking + SKI -> R.drawable.ic_guidepost_ski + INLINE_SKATING -> R.drawable.ic_guidepost_inline_skating + RUNNING -> R.drawable.ic_guidepost_running + WINTER_HIKING -> R.drawable.ic_guidepost_snow_shoe_hiking } private val GuidepostSport.titleResId: Int get() = when (this) { diff --git a/app/src/main/res/drawable/ic_guidepost_climbing.xml b/app/src/main/res/drawable/ic_guidepost_climbing.xml new file mode 100644 index 00000000000..5ab44900ef9 --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_climbing.xml @@ -0,0 +1,108 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_cycling.xml b/app/src/main/res/drawable/ic_guidepost_cycling.xml new file mode 100644 index 00000000000..188967b862d --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_cycling.xml @@ -0,0 +1,123 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_hiking.xml b/app/src/main/res/drawable/ic_guidepost_hiking.xml new file mode 100644 index 00000000000..018998b93dc --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_hiking.xml @@ -0,0 +1,69 @@ + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_horse_riding.xml b/app/src/main/res/drawable/ic_guidepost_horse_riding.xml new file mode 100644 index 00000000000..eae67c2ed33 --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_horse_riding.xml @@ -0,0 +1,222 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_inline_skating.xml b/app/src/main/res/drawable/ic_guidepost_inline_skating.xml new file mode 100644 index 00000000000..e0ef287fa04 --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_inline_skating.xml @@ -0,0 +1,172 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_mtb.xml b/app/src/main/res/drawable/ic_guidepost_mtb.xml new file mode 100644 index 00000000000..c3867e48c52 --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_mtb.xml @@ -0,0 +1,54 @@ + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_nordic_walking.xml b/app/src/main/res/drawable/ic_guidepost_nordic_walking.xml new file mode 100644 index 00000000000..2e85b801abf --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_nordic_walking.xml @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_running.xml b/app/src/main/res/drawable/ic_guidepost_running.xml new file mode 100644 index 00000000000..4dbbc937316 --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_running.xml @@ -0,0 +1,96 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_ski.xml b/app/src/main/res/drawable/ic_guidepost_ski.xml new file mode 100644 index 00000000000..963c1b617b0 --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_ski.xml @@ -0,0 +1,69 @@ + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/ic_guidepost_snow_shoe_hiking.xml b/app/src/main/res/drawable/ic_guidepost_snow_shoe_hiking.xml new file mode 100644 index 00000000000..2474cac8dd5 --- /dev/null +++ b/app/src/main/res/drawable/ic_guidepost_snow_shoe_hiking.xml @@ -0,0 +1,115 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/climbing.svg b/res/graphics/guidepost/climbing.svg new file mode 100644 index 00000000000..45f0b6aa9ca --- /dev/null +++ b/res/graphics/guidepost/climbing.svg @@ -0,0 +1,95 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/cycling.svg b/res/graphics/guidepost/cycling.svg new file mode 100644 index 00000000000..59613deebe0 --- /dev/null +++ b/res/graphics/guidepost/cycling.svg @@ -0,0 +1,81 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/hiking.svg b/res/graphics/guidepost/hiking.svg new file mode 100644 index 00000000000..140d45342f2 --- /dev/null +++ b/res/graphics/guidepost/hiking.svg @@ -0,0 +1,54 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/horse_riding.svg b/res/graphics/guidepost/horse_riding.svg new file mode 100644 index 00000000000..6239c005f87 --- /dev/null +++ b/res/graphics/guidepost/horse_riding.svg @@ -0,0 +1,167 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/inline_skating.svg b/res/graphics/guidepost/inline_skating.svg new file mode 100644 index 00000000000..7af776ec79a --- /dev/null +++ b/res/graphics/guidepost/inline_skating.svg @@ -0,0 +1,120 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/mtb.svg b/res/graphics/guidepost/mtb.svg new file mode 100644 index 00000000000..8f2e45866a6 --- /dev/null +++ b/res/graphics/guidepost/mtb.svg @@ -0,0 +1,52 @@ + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/nordic_walking.svg b/res/graphics/guidepost/nordic_walking.svg new file mode 100644 index 00000000000..b30fd53e8fe --- /dev/null +++ b/res/graphics/guidepost/nordic_walking.svg @@ -0,0 +1,96 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/running.svg b/res/graphics/guidepost/running.svg new file mode 100644 index 00000000000..d473762cb34 --- /dev/null +++ b/res/graphics/guidepost/running.svg @@ -0,0 +1,111 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/ski.svg b/res/graphics/guidepost/ski.svg new file mode 100644 index 00000000000..1a3980faf90 --- /dev/null +++ b/res/graphics/guidepost/ski.svg @@ -0,0 +1,55 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/graphics/guidepost/snow_shoe_hiking.svg b/res/graphics/guidepost/snow_shoe_hiking.svg new file mode 100644 index 00000000000..6d5236d70d8 --- /dev/null +++ b/res/graphics/guidepost/snow_shoe_hiking.svg @@ -0,0 +1,97 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + From 5fef31e6e440a58189cface77ed2385af5cb0036 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Fri, 22 Dec 2023 13:26:45 +0100 Subject: [PATCH 04/15] Added note text string --- app/src/main/res/values/strings_ee.xml | 1 + 1 file changed, 1 insertion(+) diff --git a/app/src/main/res/values/strings_ee.xml b/app/src/main/res/values/strings_ee.xml index bbe7690330e..ae52596080c 100644 --- a/app/src/main/res/values/strings_ee.xml +++ b/app/src/main/res/values/strings_ee.xml @@ -261,6 +261,7 @@ For which sport is this guidepost intended? + If there is anything not covered by the features listed, please leave a note instead. Hiking Bicycle MTB From 498d577feec7aa9e5867cafd580f9883269e3ee9 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Fri, 22 Dec 2023 13:26:55 +0100 Subject: [PATCH 05/15] Add quest to quest module list --- .../java/de/westnordost/streetcomplete/quests/QuestsModule.kt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt index 5f3c4c0d551..37e3cde0bd8 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt @@ -97,6 +97,7 @@ import de.westnordost.streetcomplete.quests.foot.AddProhibitedForPedestrians import de.westnordost.streetcomplete.quests.fuel_service.AddFuelSelfService import de.westnordost.streetcomplete.quests.general_fee.AddGeneralFee import de.westnordost.streetcomplete.quests.grit_bin_seasonal.AddGritBinSeasonal +import de.westnordost.streetcomplete.quests.guidepost_sport.AddGuidepostSports import de.westnordost.streetcomplete.quests.hairdresser.AddHairdresserCustomers import de.westnordost.streetcomplete.quests.handrail.AddHandrail import de.westnordost.streetcomplete.quests.healthcare_speciality.AddHealthcareSpeciality @@ -589,6 +590,7 @@ fun getQuestTypeList( EE_QUEST_OFFSET + 9 to AddTreeGenus(), EE_QUEST_OFFSET + 26 to AddIsPharmacyDispensing(), EE_QUEST_OFFSET + 28 to AddFootwayWidth(arSupportChecker), + EE_QUEST_OFFSET + 29 to AddGuidepostSports(), EE_QUEST_OFFSET + 10 to OsmoseQuest(osmoseDao), EE_QUEST_OFFSET + 11 to CustomQuest(customQuestList), // POI quests From 16efa8a48cd19d448933ce00323cd5ad83e6a0b3 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Fri, 22 Dec 2023 13:37:19 +0100 Subject: [PATCH 06/15] Add quest icon --- .../res/drawable/ic_quest_guidepost_sport.xml | 26 +++++++++++++++++++ res/graphics/quest/guidepost_sport.svg | 17 ++++++++++++ 2 files changed, 43 insertions(+) create mode 100644 app/src/main/res/drawable/ic_quest_guidepost_sport.xml create mode 100644 res/graphics/quest/guidepost_sport.svg diff --git a/app/src/main/res/drawable/ic_quest_guidepost_sport.xml b/app/src/main/res/drawable/ic_quest_guidepost_sport.xml new file mode 100644 index 00000000000..4d1d4e9685c --- /dev/null +++ b/app/src/main/res/drawable/ic_quest_guidepost_sport.xml @@ -0,0 +1,26 @@ + + + + + + + + diff --git a/res/graphics/quest/guidepost_sport.svg b/res/graphics/quest/guidepost_sport.svg new file mode 100644 index 00000000000..81b5d517b16 --- /dev/null +++ b/res/graphics/quest/guidepost_sport.svg @@ -0,0 +1,17 @@ + + + + + + + + + + + From a21665a441c2c0f9b2100c3206e4e1928148f279 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Fri, 22 Dec 2023 13:37:54 +0100 Subject: [PATCH 07/15] finish quest code --- .../guidepost_sport/AddGuidepostSports.kt | 122 +++--------------- .../guidepost_sport/AddGuidepostSportsForm.kt | 44 +------ .../guidepost_sport/GuidepostSportsAnswer.kt | 9 +- .../guidepost_sport/GuidepostSporttem.kt | 13 -- 4 files changed, 29 insertions(+), 159 deletions(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt index 19fdf18ee95..71f895ec76a 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt @@ -1,8 +1,6 @@ package de.westnordost.streetcomplete.quests.guidepost_sport import de.westnordost.streetcomplete.R -import de.westnordost.streetcomplete.data.elementfilter.filters.RelativeDate -import de.westnordost.streetcomplete.data.elementfilter.filters.TagOlderThan import de.westnordost.streetcomplete.data.elementfilter.toElementFilterExpression import de.westnordost.streetcomplete.data.osm.geometry.ElementGeometry import de.westnordost.streetcomplete.data.osm.mapdata.Element @@ -10,129 +8,47 @@ import de.westnordost.streetcomplete.data.osm.mapdata.MapDataWithGeometry import de.westnordost.streetcomplete.data.osm.mapdata.filter import de.westnordost.streetcomplete.data.osm.osmquests.OsmElementQuestType import de.westnordost.streetcomplete.osm.Tags -import de.westnordost.streetcomplete.osm.hasCheckDateForKey -import de.westnordost.streetcomplete.osm.removeCheckDatesForKey -import de.westnordost.streetcomplete.osm.updateCheckDateForKey -class AddGuidepostSports : OsmElementQuestType { +class AddGuidepostSports : OsmElementQuestType { - private val filter by lazy { """ + private val filter by lazy { + """ nodes with tourism = information and information ~ guidepost|route_marker and !hiking and !bicycle and !mtb and !climbing and !horse and !nordic_walking and !ski and !inline_skates and !running and !disused and !guidepost - """.toElementFilterExpression() } + """.toElementFilterExpression() + } - override val changesetComment = "Specify what can be recycled in recycling containers" + override val changesetComment = "Specify what kind of guidepost" override val wikiLink = "Tag:information=guidepost" - override val icon = R.drawable.ic_quest_recycling_container + override val icon = R.drawable.ic_quest_guidepost_sport override val isDeleteElementEnabled = true - override val defaultDisabledMessage = R.string.default_disabled_msg_seasonal + override val defaultDisabledMessage = R.string.default_disabled_msg_ee override fun getTitle(tags: Map) = R.string.quest_guidepost_sports_title override fun getApplicableElements(mapData: MapDataWithGeometry): Iterable = - mapData.nodes.filter { isApplicableTo(it) } + mapData.filter { isApplicableTo(it) == true } - override fun isApplicableTo(element: Element): Boolean = - /* Only recycling containers that do either not have any recycling:* tag yet or - * haven't been touched for 2 years and are exclusively recycling types selectable in - * StreetComplete. */ - filter.matches(element) && ( - !element.hasAnyRecyclingMaterials() - || recyclingOlderThan2Years.matches(element) && !element.hasUnknownRecyclingMaterials() - ) + override fun isApplicableTo(element: Element): Boolean? = + filter.matches(element) override fun createForm() = AddGuidepostSportsForm() override fun getHighlightedElements(element: Element, getMapData: () -> MapDataWithGeometry) = getMapData().filter("nodes with tourism = information and information ~ guidepost|route_marker") - override fun applyAnswerTo(answer: RecyclingContainerMaterialsAnswer, tags: Tags, geometry: ElementGeometry, timestampEdited: Long) { - if (answer is RecyclingMaterials) { - applyRecyclingMaterialsAnswer(answer.materials, tags) - } else if (answer is IsWasteContainer) { - applyWasteContainerAnswer(tags) - } - } - - private fun applyRecyclingMaterialsAnswer(materials: List, tags: Tags) { - // first clear recycling:* taggings previously "yes" - for ((key, value) in tags.entries) { - if (key.startsWith("recycling:") && value == "yes") { - tags.remove(key) - } - } - - // if the user chose deliberately not "all plastic", also tag it explicitly - if (materials.any { it in RecyclingMaterial.plastics }) { - for (plastic in RecyclingMaterial.plastics) { - tags.remove("recycling:${plastic.value}") - } - when { - PLASTIC_PACKAGING in materials -> { - tags["recycling:plastic"] = "no" - } - BEVERAGE_CARTONS in materials && PLASTIC_BOTTLES in materials -> { - tags["recycling:plastic_packaging"] = "no" - tags["recycling:plastic"] = "no" - } - BEVERAGE_CARTONS in materials -> { - tags["recycling:plastic_bottles"] = "no" - tags["recycling:plastic_packaging"] = "no" - tags["recycling:plastic"] = "no" - } - PLASTIC_BOTTLES in materials -> { - tags["recycling:beverage_cartons"] = "no" - tags["recycling:plastic_packaging"] = "no" - tags["recycling:plastic"] = "no" - } - PET in materials -> { - tags["recycling:plastic_bottles"] = "no" - tags["recycling:beverage_cartons"] = "no" - tags["recycling:plastic_packaging"] = "no" - tags["recycling:plastic"] = "no" - } - } - } - - // set selected recycling:* taggings to "yes" - val selectedMaterials = materials.map { "recycling:${it.value}" } - for (material in selectedMaterials) { - tags[material] = "yes" - } - - // only set the check date if nothing was changed - if (!tags.hasChanges || tags.hasCheckDateForKey("recycling")) { - tags.updateCheckDateForKey("recycling") + override fun applyAnswerTo( + answer: GuidepostSportsAnswer, + tags: Tags, + geometry: ElementGeometry, + timestampEdited: Long + ) { + answer.selectedSports.forEach { sport -> + tags[sport.key] = "yes" } } - - private fun applyWasteContainerAnswer(tags: Tags) { - tags["amenity"] = "waste_disposal" - tags.remove("recycling_type") - - val recyclingKeys = tags.keys.filter { it.startsWith("recycling:") } - for (key in recyclingKeys) { - tags.remove(key) - } - tags.removeCheckDatesForKey("recycling") - } } - -private val recyclingOlderThan2Years = - TagOlderThan("recycling", RelativeDate(-(365 * 2).toFloat())) - -private val allKnownMaterials = GuidepostSport.values().map { "recycling:" + it.value } - -private fun Element.hasAnyRecyclingMaterials(): Boolean = - tags.any { it.key.startsWith("recycling:") && it.value == "yes" } - -private fun Element.hasUnknownRecyclingMaterials(): Boolean = - tags.any { - it.key.startsWith("recycling:") - && it.key !in allKnownMaterials - && it.value == "yes" - } diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt index 3302f4d0c5d..6bdbf693d6a 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt @@ -1,47 +1,19 @@ package de.westnordost.streetcomplete.quests.guidepost_sport -import android.os.Bundle -import androidx.appcompat.app.AlertDialog import de.westnordost.streetcomplete.R import de.westnordost.streetcomplete.quests.AImageListQuestForm -import de.westnordost.streetcomplete.quests.AnswerItem import de.westnordost.streetcomplete.view.image_select.ImageListPickerDialog -import de.westnordost.streetcomplete.view.image_select.ImageSelectAdapter import de.westnordost.streetcomplete.view.image_select.Item -class AddGuidepostSportsForm : - AImageListQuestForm, RecyclingContainerMaterialsAnswer>() { +class AddGuidepostSportsForm : AImageListQuestForm, GuidepostSportsAnswer>() { override val descriptionResId = R.string.quest_recycling_materials_note - override val otherAnswers = listOf( - AnswerItem(R.string.quest_recycling_materials_answer_waste) { confirmJustTrash() } - ) - override val items get() = GuidepostSport.selectableValues.map { it.asItem() } + override val itemsPerRow = 3 override val maxSelectableItems = -1 - private val isAnyGlassRecycleable get() = countryInfo.isUsuallyAnyGlassRecyclableInContainers - - override fun onCreate(savedInstanceState: Bundle?) { - super.onCreate(savedInstanceState) - imageSelector.cellLayoutId = R.layout.cell_icon_select_with_label_below - imageSelector.listeners.add(object : ImageSelectAdapter.OnItemSelectionListener { - override fun onIndexSelected(index: Int) { - val value = imageSelector.items[index].value!! - - if (value in GuidepostSport.selectableGuidepostValues) { - showPickItemForItemAtIndexDialog(index, GuidepostSport.selectablePlasticValues.map { it.asItem() }) - } else if (isAnyGlassRecycleable && value in GuidepostSport.selectableGlassValues) { - showPickItemForItemAtIndexDialog(index, GuidepostSport.selectableGlassValues.map { it.asItem() }) - } - } - - override fun onIndexDeselected(index: Int) {} - }) - } - private fun showPickItemForItemAtIndexDialog(index: Int, items: List>>) { val ctx = context ?: return ImageListPickerDialog(ctx, items, R.layout.cell_icon_select_with_label_below, 3) { selected -> @@ -52,15 +24,7 @@ class AddGuidepostSportsForm : } override fun onClickOk(selectedItems: List>) { - applyAnswer(RecyclingMaterials(selectedItems.flatten())) - } - - private fun confirmJustTrash() { - activity?.let { AlertDialog.Builder(it) - .setMessage(R.string.quest_recycling_materials_answer_waste_description) - .setPositiveButton(R.string.quest_generic_confirmation_yes) { _, _ -> applyAnswer(IsWasteContainer) } - .setNegativeButton(R.string.quest_generic_confirmation_no, null) - .show() - } + val answer = SelectedGuidepostSports(selectedItems.flatten()) + applyAnswer(answer) } } diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt index c97ea81346e..3d1eb9c0b23 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt @@ -1,6 +1,9 @@ package de.westnordost.streetcomplete.quests.guidepost_sport -sealed interface RecyclingContainerMaterialsAnswer +sealed interface GuidepostSportsAnswer { + val selectedSports: List +} -object IsWasteContainer : RecyclingContainerMaterialsAnswer -data class RecyclingMaterials(val materials: List) : RecyclingContainerMaterialsAnswer +data class SelectedGuidepostSports( + override val selectedSports: List +) : GuidepostSportsAnswer diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt index 67de3cb7ceb..aa9c5cb24b9 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSporttem.kt @@ -7,9 +7,6 @@ import de.westnordost.streetcomplete.view.image_select.Item fun GuidepostSport.asItem(): Item> = Item(listOf(this), iconResId, titleResId) -fun List.asItem(): Item> = - Item(this, iconResId, titleResId) - private val GuidepostSport.iconResId: Int get() = when (this) { HIKING -> R.drawable.ic_guidepost_hiking BICYCLE -> R.drawable.ic_guidepost_cycling @@ -35,13 +32,3 @@ private val GuidepostSport.titleResId: Int get() = when (this) { RUNNING -> R.string.quest_guidepost_sports_running WINTER_HIKING -> R.string.quest_guidepost_sports_winter_hiking } - -private val List.iconResId: Int get() = when (this) { - listOf(HIKING, BICYCLE) -> R.drawable.ic_recycling_plastic_bottles_and_cartons - else -> first().iconResId -} - -private val List.titleResId: Int get() = when (this) { - listOf(HIKING, BICYCLE) -> R.string.quest_recycling_type_plastic_bottles_and_cartons - else -> first().titleResId -} From eb724db4d1888ba179c2700a19d30a5f2a4d4137 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Fri, 22 Dec 2023 14:02:53 +0100 Subject: [PATCH 08/15] changed note string --- .../quests/guidepost_sport/AddGuidepostSportsForm.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt index 6bdbf693d6a..c863d5f6882 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt @@ -7,7 +7,7 @@ import de.westnordost.streetcomplete.view.image_select.Item class AddGuidepostSportsForm : AImageListQuestForm, GuidepostSportsAnswer>() { - override val descriptionResId = R.string.quest_recycling_materials_note + override val descriptionResId = R.string.quest_guidepost_sports_note override val items get() = GuidepostSport.selectableValues.map { it.asItem() } override val itemsPerRow = 3 From fc2345c5574cce0bd41ae886c9923aee0a324bd1 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Fri, 22 Dec 2023 14:27:06 +0100 Subject: [PATCH 09/15] increased quest number --- .../java/de/westnordost/streetcomplete/quests/QuestsModule.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt index 37e3cde0bd8..ecefb02dc6d 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/QuestsModule.kt @@ -590,7 +590,7 @@ fun getQuestTypeList( EE_QUEST_OFFSET + 9 to AddTreeGenus(), EE_QUEST_OFFSET + 26 to AddIsPharmacyDispensing(), EE_QUEST_OFFSET + 28 to AddFootwayWidth(arSupportChecker), - EE_QUEST_OFFSET + 29 to AddGuidepostSports(), + EE_QUEST_OFFSET + 41 to AddGuidepostSports(), EE_QUEST_OFFSET + 10 to OsmoseQuest(osmoseDao), EE_QUEST_OFFSET + 11 to CustomQuest(customQuestList), // POI quests From 2535ce5e5290deed307afaa4d5116c5ab56fd34e Mon Sep 17 00:00:00 2001 From: mcliquid Date: Sat, 23 Dec 2023 12:46:54 +0100 Subject: [PATCH 10/15] add other answer and cellLayoutId --- .../guidepost_sport/AddGuidepostSports.kt | 18 ++++++----- .../guidepost_sport/AddGuidepostSportsForm.kt | 31 +++++++++++++++++++ .../guidepost_sport/GuidepostSportsAnswer.kt | 3 ++ app/src/main/res/values/strings_ee.xml | 2 ++ 4 files changed, 46 insertions(+), 8 deletions(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt index 71f895ec76a..0c3927c7fba 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt @@ -41,14 +41,16 @@ class AddGuidepostSports : OsmElementQuestType { override fun getHighlightedElements(element: Element, getMapData: () -> MapDataWithGeometry) = getMapData().filter("nodes with tourism = information and information ~ guidepost|route_marker") - override fun applyAnswerTo( - answer: GuidepostSportsAnswer, - tags: Tags, - geometry: ElementGeometry, - timestampEdited: Long - ) { - answer.selectedSports.forEach { sport -> - tags[sport.key] = "yes" + override fun applyAnswerTo(answer: GuidepostSportsAnswer, tags: Tags, geometry: ElementGeometry, timestampEdited: Long) { + if (answer is IsSimpleGuidepost) { + applySimpleGuidepostAnswer(tags) + } else { + answer.selectedSports.forEach { sport -> + tags[sport.key] = "yes" + } } } + private fun applySimpleGuidepostAnswer(tags: Tags) { + tags["guidepost"] = "simple" + } } diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt index c863d5f6882..84ae6b2c7e6 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt @@ -1,19 +1,41 @@ package de.westnordost.streetcomplete.quests.guidepost_sport +import android.os.Bundle +import androidx.appcompat.app.AlertDialog import de.westnordost.streetcomplete.R import de.westnordost.streetcomplete.quests.AImageListQuestForm +import de.westnordost.streetcomplete.quests.AnswerItem +import de.westnordost.streetcomplete.quests.recycling_material.RecyclingMaterial +import de.westnordost.streetcomplete.quests.recycling_material.asItem import de.westnordost.streetcomplete.view.image_select.ImageListPickerDialog +import de.westnordost.streetcomplete.view.image_select.ImageSelectAdapter import de.westnordost.streetcomplete.view.image_select.Item class AddGuidepostSportsForm : AImageListQuestForm, GuidepostSportsAnswer>() { override val descriptionResId = R.string.quest_guidepost_sports_note + override val otherAnswers = listOf( + AnswerItem(R.string.quest_guidepost_sports_answer_simple) { confirmJustSimple() } + ) + override val items get() = GuidepostSport.selectableValues.map { it.asItem() } override val itemsPerRow = 3 override val maxSelectableItems = -1 + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + imageSelector.cellLayoutId = R.layout.cell_icon_select_with_label_below + imageSelector.listeners.add(object : ImageSelectAdapter.OnItemSelectionListener { + override fun onIndexSelected(index: Int) { + val value = imageSelector.items[index].value!! + } + + override fun onIndexDeselected(index: Int) {} + }) + } + private fun showPickItemForItemAtIndexDialog(index: Int, items: List>>) { val ctx = context ?: return ImageListPickerDialog(ctx, items, R.layout.cell_icon_select_with_label_below, 3) { selected -> @@ -27,4 +49,13 @@ class AddGuidepostSportsForm : AImageListQuestForm, Guidepo val answer = SelectedGuidepostSports(selectedItems.flatten()) applyAnswer(answer) } + + private fun confirmJustSimple() { + activity?.let { AlertDialog.Builder(it) + .setMessage(R.string.quest_guidepost_sports_answer_simple_description) + .setPositiveButton(R.string.quest_generic_confirmation_yes) { _, _ -> applyAnswer(IsSimpleGuidepost) } + .setNegativeButton(R.string.quest_generic_confirmation_no, null) + .show() + } + } } diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt index 3d1eb9c0b23..671acce2208 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt @@ -1,9 +1,12 @@ package de.westnordost.streetcomplete.quests.guidepost_sport + sealed interface GuidepostSportsAnswer { val selectedSports: List } +object IsSimpleGuidepost : GuidepostSportsAnswer + data class SelectedGuidepostSports( override val selectedSports: List ) : GuidepostSportsAnswer diff --git a/app/src/main/res/values/strings_ee.xml b/app/src/main/res/values/strings_ee.xml index ae52596080c..133b8436718 100644 --- a/app/src/main/res/values/strings_ee.xml +++ b/app/src/main/res/values/strings_ee.xml @@ -262,6 +262,8 @@ For which sport is this guidepost intended? If there is anything not covered by the features listed, please leave a note instead. + "It´s just a simple guidepost." + "This is just a simple guidepost with no specific sports." Hiking Bicycle MTB From 661c85196fc78c870953b12fc64a95f92836ee43 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Sat, 23 Dec 2023 17:23:39 +0100 Subject: [PATCH 11/15] tried fixing the code --- .../quests/guidepost_sport/AddGuidepostSports.kt | 6 +----- .../quests/guidepost_sport/GuidepostSportsAnswer.kt | 9 ++------- 2 files changed, 3 insertions(+), 12 deletions(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt index 0c3927c7fba..56ce371351d 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt @@ -44,11 +44,7 @@ class AddGuidepostSports : OsmElementQuestType { override fun applyAnswerTo(answer: GuidepostSportsAnswer, tags: Tags, geometry: ElementGeometry, timestampEdited: Long) { if (answer is IsSimpleGuidepost) { applySimpleGuidepostAnswer(tags) - } else { - answer.selectedSports.forEach { sport -> - tags[sport.key] = "yes" - } - } + } else if (answer is SelectedGuidepostSports) {} } private fun applySimpleGuidepostAnswer(tags: Tags) { tags["guidepost"] = "simple" diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt index 671acce2208..670858c67ff 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/GuidepostSportsAnswer.kt @@ -1,12 +1,7 @@ package de.westnordost.streetcomplete.quests.guidepost_sport -sealed interface GuidepostSportsAnswer { - val selectedSports: List -} +sealed interface GuidepostSportsAnswer object IsSimpleGuidepost : GuidepostSportsAnswer - -data class SelectedGuidepostSports( - override val selectedSports: List -) : GuidepostSportsAnswer +data class SelectedGuidepostSports(val selectedSports: List) : GuidepostSportsAnswer From c9bf5071899ece364e51f2def307d1e49e286755 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Sat, 23 Dec 2023 23:07:42 +0100 Subject: [PATCH 12/15] fixed selection --- .../quests/guidepost_sport/AddGuidepostSports.kt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt index 56ce371351d..42c92608c06 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt @@ -44,7 +44,9 @@ class AddGuidepostSports : OsmElementQuestType { override fun applyAnswerTo(answer: GuidepostSportsAnswer, tags: Tags, geometry: ElementGeometry, timestampEdited: Long) { if (answer is IsSimpleGuidepost) { applySimpleGuidepostAnswer(tags) - } else if (answer is SelectedGuidepostSports) {} + } else if (answer is SelectedGuidepostSports) { + answer.selectedSports.forEach { tags[it.key] = "yes" } + } } private fun applySimpleGuidepostAnswer(tags: Tags) { tags["guidepost"] = "simple" From 2808d3f40f1a9aeee447e1c5dfcdac0e0f1e754c Mon Sep 17 00:00:00 2001 From: mcliquid Date: Sun, 24 Dec 2023 09:45:35 +0100 Subject: [PATCH 13/15] Changed title --- app/src/main/res/values/strings_ee.xml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/src/main/res/values/strings_ee.xml b/app/src/main/res/values/strings_ee.xml index 133b8436718..71aec60a93a 100644 --- a/app/src/main/res/values/strings_ee.xml +++ b/app/src/main/res/values/strings_ee.xml @@ -265,12 +265,12 @@ "It´s just a simple guidepost." "This is just a simple guidepost with no specific sports." Hiking - Bicycle + Cycling MTB Climbing - Horse + Horse Riding Nordic Walking - Ski + Skiing Inline Skating Running Winter Hiking From fff49ea7b4114883828e121acc11aa60759854e5 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Sun, 24 Dec 2023 10:02:26 +0100 Subject: [PATCH 14/15] removed dot --- app/src/main/res/values/strings_ee.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/src/main/res/values/strings_ee.xml b/app/src/main/res/values/strings_ee.xml index 71aec60a93a..2031ce7326b 100644 --- a/app/src/main/res/values/strings_ee.xml +++ b/app/src/main/res/values/strings_ee.xml @@ -262,7 +262,7 @@ For which sport is this guidepost intended? If there is anything not covered by the features listed, please leave a note instead. - "It´s just a simple guidepost." + "It´s just a simple guidepost" "This is just a simple guidepost with no specific sports." Hiking Cycling From 7ed96224424ede79a42f22b529ff00c861252e28 Mon Sep 17 00:00:00 2001 From: mcliquid Date: Sun, 24 Dec 2023 10:02:42 +0100 Subject: [PATCH 15/15] switched to FilterQuestType --- .../quests/guidepost_sport/AddGuidepostSports.kt | 14 ++++---------- .../guidepost_sport/AddGuidepostSportsForm.kt | 1 - 2 files changed, 4 insertions(+), 11 deletions(-) diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt index 42c92608c06..ad1879787d8 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSports.kt @@ -7,11 +7,12 @@ import de.westnordost.streetcomplete.data.osm.mapdata.Element import de.westnordost.streetcomplete.data.osm.mapdata.MapDataWithGeometry import de.westnordost.streetcomplete.data.osm.mapdata.filter import de.westnordost.streetcomplete.data.osm.osmquests.OsmElementQuestType +import de.westnordost.streetcomplete.data.osm.osmquests.OsmFilterQuestType import de.westnordost.streetcomplete.osm.Tags -class AddGuidepostSports : OsmElementQuestType { +class AddGuidepostSports : OsmFilterQuestType() { - private val filter by lazy { + override val elementFilter = """ nodes with tourism = information @@ -19,8 +20,7 @@ class AddGuidepostSports : OsmElementQuestType { and !hiking and !bicycle and !mtb and !climbing and !horse and !nordic_walking and !ski and !inline_skates and !running and !disused and !guidepost - """.toElementFilterExpression() - } + """ override val changesetComment = "Specify what kind of guidepost" override val wikiLink = "Tag:information=guidepost" @@ -30,12 +30,6 @@ class AddGuidepostSports : OsmElementQuestType { override fun getTitle(tags: Map) = R.string.quest_guidepost_sports_title - override fun getApplicableElements(mapData: MapDataWithGeometry): Iterable = - mapData.filter { isApplicableTo(it) == true } - - override fun isApplicableTo(element: Element): Boolean? = - filter.matches(element) - override fun createForm() = AddGuidepostSportsForm() override fun getHighlightedElements(element: Element, getMapData: () -> MapDataWithGeometry) = diff --git a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt index 84ae6b2c7e6..a54d701f358 100644 --- a/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt +++ b/app/src/main/java/de/westnordost/streetcomplete/quests/guidepost_sport/AddGuidepostSportsForm.kt @@ -21,7 +21,6 @@ class AddGuidepostSportsForm : AImageListQuestForm, Guidepo override val items get() = GuidepostSport.selectableValues.map { it.asItem() } override val itemsPerRow = 3 - override val maxSelectableItems = -1 override fun onCreate(savedInstanceState: Bundle?) {