Skip to content

Commit

Permalink
Merge pull request #17774 from osmandapp/16632-fix-crashhistory-click
Browse files Browse the repository at this point in the history
#16632: Fixed selecting gpx track item in history
  • Loading branch information
alex-osm authored Aug 1, 2023
2 parents 7ef0a72 + ead1573 commit 63a9df4
Showing 1 changed file with 118 additions and 43 deletions.
161 changes: 118 additions & 43 deletions OsmAnd/src/net/osmand/plus/auto/HistoryScreen.kt
Original file line number Diff line number Diff line change
@@ -1,16 +1,23 @@
package net.osmand.plus.auto

import android.os.AsyncTask
import android.text.SpannableString
import android.text.Spanned
import androidx.car.app.CarContext
import androidx.car.app.constraints.ConstraintManager
import androidx.car.app.model.*
import androidx.core.graphics.drawable.IconCompat
import androidx.lifecycle.DefaultLifecycleObserver
import androidx.lifecycle.LifecycleOwner
import net.osmand.data.LatLon
import net.osmand.plus.R
import net.osmand.plus.helpers.SearchHistoryHelper
import net.osmand.plus.helpers.SearchHistoryHelper.HistoryEntry
import net.osmand.plus.search.QuickSearchHelper.SearchHistoryAPI
import net.osmand.plus.search.listitems.QuickSearchListItem
import net.osmand.plus.track.data.GPXInfo
import net.osmand.plus.track.helpers.GPXDatabase.GpxDataItem
import net.osmand.plus.track.helpers.GpxDbHelper
import net.osmand.search.core.ObjectType
import net.osmand.search.core.SearchPhrase
import net.osmand.search.core.SearchResult
Expand All @@ -19,47 +26,38 @@ import net.osmand.util.MapUtils
class HistoryScreen(
carContext: CarContext,
private val settingsAction: Action) : BaseOsmAndAndroidAutoScreen(carContext) {
private lateinit var updateItemsTask: HistoryScreen.UpdateHistoryItemsTask
private lateinit var searchItems: ArrayList<QuickSearchListItem>
val gpxDbHelper: GpxDbHelper = app.gpxDbHelper

init {
lifecycle.addObserver(object : DefaultLifecycleObserver {
override fun onCreate(owner: LifecycleOwner) {
super.onCreate(owner)
updateItemsTask = UpdateHistoryItemsTask()
updateItemsTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR)
}
})
}

private inner class UpdateHistoryItemsTask : AsyncTask<Unit, Unit, Unit>() {
override fun doInBackground(vararg params: Unit?) {
prepareHistoryItems()
}

override fun onPostExecute(result: Unit?) {
invalidate()
}
}


override fun onGetTemplate(): Template {
val listBuilder = ItemList.Builder()
val templateBuilder = ListTemplate.Builder()
val app = app
val historyHelper = SearchHistoryHelper.getInstance(app)
val results = historyHelper.getHistoryEntries(true)
val location = app.mapViewTrackingUtilities.defaultLocation
val resultsSize = results.size
val limitedResults = results.subList(0, resultsSize.coerceAtMost(contentLimit - 1))
for (result in limitedResults) {
val searchResult =
SearchHistoryAPI.createSearchResult(app, result, SearchPhrase.emptyPhrase())
val listItem = QuickSearchListItem(app, searchResult)
val pointDescription = result.name

val title = listItem.name
val icon = CarIcon.Builder(
IconCompat.createWithResource(app, pointDescription.itemIcon)).build()
val rowBuilder = Row.Builder()
.setTitle(title)
.setImage(icon)
.setOnClickListener { onClickHistoryItem(listItem) }
val dist = if (searchResult.location == null) {
0.0
} else {
rowBuilder.setMetadata(
Metadata.Builder().setPlace(
Place.Builder(
CarLocation.create(
result.lat,
result.lon)).build()).build())
MapUtils.getDistance(
result.lat, result.lon,
location.latitude, location.longitude)
}
val address = SpannableString(" ")
val distanceSpan = DistanceSpan.create(TripHelper.getDistance(app, dist))
address.setSpan(distanceSpan, 0, 1, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
rowBuilder.addText(address)
listBuilder.addItem(rowBuilder.build())
}
val isLoading = updateItemsTask.status != AsyncTask.Status.FINISHED
if (!isLoading) {
prepareList(templateBuilder)
}
val actionStripBuilder = ActionStrip.Builder()
actionStripBuilder.addAction(
Action.Builder()
Expand All @@ -69,23 +67,100 @@ class HistoryScreen(
carContext, R.drawable.ic_action_search_dark)).build())
.setOnClickListener { openSearch() }
.build())
return ListTemplate.Builder()
.setSingleList(listBuilder.build())
return templateBuilder
.setLoading(isLoading)
.setTitle(app.getString(R.string.shared_string_history))
.setHeaderAction(Action.BACK)
.setActionStrip(actionStripBuilder.build())
.build()
}

private fun prepareHistoryItems() {
val historyHelper = SearchHistoryHelper.getInstance(app)
val results = historyHelper.getHistoryEntries(true)
val resultsSize = results.size
searchItems = ArrayList()
var limitedResults = results.subList(0, resultsSize.coerceAtMost(contentLimit - 1))
for (result in limitedResults) {
val searchResult =
SearchHistoryAPI.createSearchResult(app, result, SearchPhrase.emptyPhrase())
val listItem = QuickSearchListItem(app, searchResult)
if (listItem.searchResult.objectType == ObjectType.GPX_TRACK && listItem.searchResult.location == null) {
var gpxInfo = listItem.searchResult.relatedObject as GPXInfo
var gpxFile = gpxInfo.gpxFile
if (gpxFile == null) {
gpxInfo.file?.let { file ->
val item = gpxDbHelper.getItem(file) {
updateSearchResult(
listItem.searchResult,
it)
}
if (item != null) {
updateSearchResult(listItem.searchResult, item)
}
}
} else {
val analysis = gpxFile.getAnalysis(0)
listItem.searchResult.location = analysis?.latLonStart
}
}
searchItems.add(listItem)
}
}

private fun updateSearchResult(searchResult: SearchResult, dataItem: GpxDataItem) {
searchResult.location = dataItem.analysis?.latLonStart
}

private fun prepareList(templateBuilder: ListTemplate.Builder) {
val listBuilder = ItemList.Builder()
val location = app.mapViewTrackingUtilities.defaultLocation
for (item in searchItems) {
if (item.searchResult?.`object` is HistoryEntry) {
val result = item.searchResult?.`object` as HistoryEntry
val pointDescription = result.name
val title = item.name
val icon = CarIcon.Builder(
IconCompat.createWithResource(app, pointDescription.itemIcon)).build()
val rowBuilder = Row.Builder()
.setTitle(title)
.setImage(icon)
.setOnClickListener { onClickHistoryItem(item) }
val dist = if (item.searchResult.location == null) {
0.0
} else {
var startLocation = item.searchResult.location
rowBuilder.setMetadata(
Metadata.Builder().setPlace(
Place.Builder(
CarLocation.create(
startLocation.latitude,
startLocation.longitude)).build()).build())
MapUtils.getDistance(
startLocation.latitude, startLocation.longitude,
location.latitude, location.longitude)
}
val address = SpannableString(" ")
val distanceSpan = DistanceSpan.create(TripHelper.getDistance(app, dist))
address.setSpan(distanceSpan, 0, 1, Spanned.SPAN_INCLUSIVE_INCLUSIVE)
rowBuilder.addText(address)
listBuilder.addItem(rowBuilder.build())
}
}
templateBuilder.setSingleList(listBuilder.build())
}

override fun getConstraintLimitType(): Int {
return ConstraintManager.CONTENT_LIMIT_TYPE_PLACE_LIST
}

private fun onClickHistoryItem(historyItem: QuickSearchListItem) {
val result = SearchResult()
result.location = LatLon(
historyItem.searchResult.location.latitude,
historyItem.searchResult.location.longitude)
if (historyItem.searchResult.location != null) {
result.location = LatLon(
historyItem.searchResult.location.latitude,
historyItem.searchResult.location.longitude)
}
result.objectType = ObjectType.RECENT_OBJ
result.`object` = historyItem.searchResult.`object`
openRoutePreview(settingsAction, result)
Expand Down

0 comments on commit 63a9df4

Please sign in to comment.