DEVIATION depends on speed
This commit is contained in:
@@ -6,7 +6,7 @@ plugins {
|
||||
|
||||
android {
|
||||
namespace = "com.kouros.android.cars.carappservice"
|
||||
compileSdk = 36
|
||||
compileSdk = 37
|
||||
|
||||
defaultConfig {
|
||||
minSdk = 33
|
||||
|
||||
@@ -132,12 +132,12 @@ class CarSensorManager(
|
||||
|
||||
val carSensors = carHardwareManager.carSensors
|
||||
carSensors.addCompassListener(
|
||||
CarSensors.UPDATE_RATE_NORMAL,
|
||||
CarSensors.UPDATE_RATE_FASTEST,
|
||||
carContext.mainExecutor,
|
||||
carCompassListener
|
||||
)
|
||||
carSensors.addCarHardwareLocationListener(
|
||||
CarSensors.UPDATE_RATE_UI,
|
||||
CarSensors.UPDATE_RATE_FASTEST,
|
||||
carContext.mainExecutor,
|
||||
carLocationListener
|
||||
)
|
||||
|
||||
@@ -12,14 +12,8 @@ import androidx.lifecycle.LifecycleOwner
|
||||
import androidx.lifecycle.lifecycleScope
|
||||
import androidx.lifecycle.repeatOnLifecycle
|
||||
import com.kouros.data.BuildConfig
|
||||
import com.kouros.navigation.data.Constants.a22
|
||||
import com.kouros.navigation.data.Constants.a9
|
||||
import com.kouros.navigation.data.Constants.a94
|
||||
import com.kouros.navigation.data.Constants.homeHohenwaldeck
|
||||
import com.kouros.navigation.data.Constants.homeVogelhart
|
||||
import com.kouros.navigation.data.Constants.ioannina
|
||||
import com.kouros.navigation.data.Constants.isarring
|
||||
import com.kouros.navigation.data.Constants.subislawa
|
||||
import com.kouros.navigation.data.Constants.widenmayer
|
||||
import kotlinx.coroutines.channels.awaitClose
|
||||
import kotlinx.coroutines.flow.Flow
|
||||
import kotlinx.coroutines.flow.callbackFlow
|
||||
|
||||
@@ -4,7 +4,9 @@ import android.Manifest.permission
|
||||
import android.content.Intent
|
||||
import android.content.pm.PackageManager
|
||||
import android.location.Location
|
||||
import android.os.Build
|
||||
import android.util.Log
|
||||
import androidx.annotation.RequiresApi
|
||||
import androidx.car.app.CarContext
|
||||
import androidx.car.app.CarToast
|
||||
import androidx.car.app.Screen
|
||||
@@ -111,7 +113,6 @@ class NavigationSession : CarSession(), NavigationListener, NavigationObserverCa
|
||||
|
||||
var speedCameras = listOf<Elements>()
|
||||
|
||||
|
||||
private var lastRouteCheckLocation = location(0.0, 0.0)
|
||||
|
||||
var navigationManagerStarted = false
|
||||
@@ -463,8 +464,8 @@ class NavigationSession : CarSession(), NavigationListener, NavigationObserverCa
|
||||
*/
|
||||
private fun handleNavigationLocation(location: Location) {
|
||||
val start = System.currentTimeMillis()
|
||||
routeModel.updateLocation(location, navigationViewModel)
|
||||
val snappedLocation = snapLocation(location, routeModel.route.maneuverLocations())
|
||||
routeModel.updateLocation(snappedLocation, navigationViewModel)
|
||||
val streetName = routeModel.currentStep().street
|
||||
if (checkLocationDeviation(location, snappedLocation, streetName)) {
|
||||
if (routeModel.navState.arrived) return
|
||||
@@ -490,11 +491,21 @@ class NavigationSession : CarSession(), NavigationListener, NavigationObserverCa
|
||||
snappedLocation: Location,
|
||||
streetName: String
|
||||
): Boolean {
|
||||
var maximalRouteDeviation = MAXIMAL_ROUTE_DEVIATION
|
||||
val speed = surfaceRenderer.speed.value
|
||||
if (speed != null) {
|
||||
when (speed) {
|
||||
in 0.0..10.0 -> maximalRouteDeviation = MAXIMAL_ROUTE_DEVIATION
|
||||
in 10.0..20.0 -> maximalRouteDeviation = MAXIMAL_ROUTE_DEVIATION + 200
|
||||
in 20.0..30.0 -> maximalRouteDeviation = MAXIMAL_ROUTE_DEVIATION + 400
|
||||
in 30.0..100.0 -> maximalRouteDeviation = MAXIMAL_ROUTE_DEVIATION + 500
|
||||
}
|
||||
}
|
||||
val distance = location.distanceTo(snappedLocation)
|
||||
when {
|
||||
distance > MAXIMAL_ROUTE_DEVIATION && distance < MAXIMAL_ROUTE_DEVIATION * 10-> {
|
||||
distance > maximalRouteDeviation -> {
|
||||
stopNavigation()
|
||||
navigationScreen.calculateNewRoute(routeModel.navState.destination)
|
||||
navigationScreen.calculateNewRoute(routeModel.navState.destination, distance)
|
||||
return false
|
||||
}
|
||||
|
||||
@@ -813,18 +824,25 @@ class NavigationSession : CarSession(), NavigationListener, NavigationObserverCa
|
||||
if (camera.distance < 80) {
|
||||
if ((bearingSpeedCamera - bearingRoute).absoluteValue < 15.0) {
|
||||
routeModel.showSpeedCamera(carContext, camera.distance, camera.tags.maxspeed)
|
||||
camera.distance = 1000.0
|
||||
val cameras = mutableListOf<Elements>()
|
||||
speedCameras.forEach {
|
||||
if (!(camera.lon == it.lon && camera.lat == it.lat)) {
|
||||
cameras.add(it)
|
||||
}
|
||||
}
|
||||
speedCameras = cameras
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Checks if a new route is needed based on the time since the last update.
|
||||
*/
|
||||
private fun checkRoute(location: Location) {
|
||||
val distance = location.distanceTo(lastRouteCheckLocation)
|
||||
if (distance > checkDistance(routeModel)) {
|
||||
if (distance > checkDistance(routeModel)) {
|
||||
if (lastRouteCheckLocation.latitude != 0.0) {
|
||||
val destination = location(
|
||||
routeModel.navState.destination.longitude,
|
||||
|
||||
@@ -2,7 +2,6 @@ package com.kouros.navigation.car.screen
|
||||
|
||||
import android.os.CountDownTimer
|
||||
import android.os.Handler
|
||||
import android.util.Log
|
||||
import androidx.car.app.CarContext
|
||||
import androidx.car.app.Screen
|
||||
import androidx.car.app.model.Action
|
||||
@@ -33,7 +32,6 @@ import com.kouros.data.R
|
||||
import com.kouros.navigation.car.SurfaceRenderer
|
||||
import com.kouros.navigation.car.screen.settings.SettingsScreen
|
||||
import com.kouros.navigation.data.Constants
|
||||
import com.kouros.navigation.data.Constants.TAG
|
||||
import com.kouros.navigation.data.Place
|
||||
import com.kouros.navigation.data.ViewStyle
|
||||
import com.kouros.navigation.model.NavigationViewModel
|
||||
@@ -53,6 +51,7 @@ open class NavigationScreen(
|
||||
private val navigationViewModel: NavigationViewModel
|
||||
) : Screen(carContext) {
|
||||
|
||||
var deviation = 0F
|
||||
var recentPlaces = mutableListOf<Place>()
|
||||
|
||||
var recentPlace: Place = Place()
|
||||
@@ -151,10 +150,11 @@ open class NavigationScreen(
|
||||
.setDestinationTravelEstimate(destinationTravelEstimate)
|
||||
.setActionStrip(actionStripBuilder.build())
|
||||
.setMapActionStrip(
|
||||
mapActionStrip(carContext,
|
||||
mapActionStrip(
|
||||
carContext,
|
||||
surfaceRenderer.viewStyle,
|
||||
{ zoomPlus() }, { zoomMinus() }, {
|
||||
Action.Builder()
|
||||
Action.Builder()
|
||||
.setIcon(createCarIcon(carContext, R.drawable.ic_recenter_24))
|
||||
.setFlags(0)
|
||||
.setOnClickListener {
|
||||
@@ -173,17 +173,18 @@ open class NavigationScreen(
|
||||
* Creates and returns a template for the default view state.
|
||||
*/
|
||||
private fun navigationView(actionStripBuilder: ActionStrip.Builder): Template {
|
||||
val mapActionStrip = mapActionStrip(carContext,
|
||||
surfaceRenderer.viewStyle,
|
||||
{ zoomPlus() }, { zoomMinus() }, {
|
||||
createAction(
|
||||
carContext = carContext, R.drawable.ic_recenter_24,
|
||||
0,
|
||||
onClickAction = {
|
||||
surfaceRenderer.setStandardView()
|
||||
invalidate()
|
||||
})
|
||||
})
|
||||
val mapActionStrip = mapActionStrip(
|
||||
carContext,
|
||||
surfaceRenderer.viewStyle,
|
||||
{ zoomPlus() }, { zoomMinus() }, {
|
||||
createAction(
|
||||
carContext = carContext, R.drawable.ic_recenter_24,
|
||||
0,
|
||||
onClickAction = {
|
||||
surfaceRenderer.setStandardView()
|
||||
invalidate()
|
||||
})
|
||||
})
|
||||
return NavigationTemplate.Builder()
|
||||
.setBackgroundColor(backGroundColor)
|
||||
.setActionStrip(actionStripBuilder.build())
|
||||
@@ -215,14 +216,10 @@ open class NavigationScreen(
|
||||
* Creates and returns a NavigationTemplate specifically for when the destination is reached.
|
||||
*/
|
||||
fun navigationArrived(actionStripBuilder: ActionStrip.Builder): NavigationTemplate {
|
||||
var street = ""
|
||||
if (destinations.first().address != null) {
|
||||
street = destinations.first().address.toString()
|
||||
}
|
||||
return NavigationTemplate.Builder()
|
||||
.setNavigationInfo(
|
||||
MessageInfo.Builder(
|
||||
carContext.getString(R.string.arrived_exclamation_msg)
|
||||
carContext.getString(R.string.arrived_exclamation_msg)
|
||||
)
|
||||
.setText(message)
|
||||
.setImage(
|
||||
@@ -239,7 +236,8 @@ open class NavigationScreen(
|
||||
.setBackgroundColor(backGroundColor)
|
||||
.setActionStrip(actionStripBuilder.build())
|
||||
.setMapActionStrip(
|
||||
mapActionStrip(carContext,
|
||||
mapActionStrip(
|
||||
carContext,
|
||||
surfaceRenderer.viewStyle,
|
||||
{ zoomPlus() }, { zoomMinus() }, {
|
||||
createAction(
|
||||
@@ -300,7 +298,8 @@ open class NavigationScreen(
|
||||
val builder = MapWithContentTemplate.Builder()
|
||||
.setContentTemplate(contentTemplate)
|
||||
.setActionStrip(
|
||||
mapActionStrip(carContext,
|
||||
mapActionStrip(
|
||||
carContext,
|
||||
ViewStyle.VIEW,
|
||||
{ settingsAction() },
|
||||
{
|
||||
@@ -472,13 +471,14 @@ open class NavigationScreen(
|
||||
/**
|
||||
* Initiates recalculation for a new route to the destination.
|
||||
*/
|
||||
fun calculateNewRoute(destination: Place) {
|
||||
fun calculateNewRoute(destination: Place, distance: Float) {
|
||||
deviation = distance
|
||||
navigationType = NavigationType.REROUTE
|
||||
invalidate()
|
||||
val mainThreadHandler = Handler(carContext.mainLooper)
|
||||
mainThreadHandler.post {
|
||||
reRouteTimer?.cancel()
|
||||
reRouteTimer = object : CountDownTimer(2000, 1000) {
|
||||
reRouteTimer = object : CountDownTimer(5000, 1000) {
|
||||
override fun onTick(millisUntilFinished: Long) {}
|
||||
override fun onFinish() {
|
||||
navigationType = NavigationType.NAVIGATION
|
||||
|
||||
@@ -75,7 +75,7 @@ class PlaceListScreen(
|
||||
override fun onGetTemplate(): Template {
|
||||
val itemListBuilder = ItemList.Builder()
|
||||
.setNoItemsMessage(carContext.getString(R.string.no_places))
|
||||
recentPlaces.filter { it.category == category }.forEach {
|
||||
recentPlaces.filter { it.category == category && it.distance > 500F }.forEach {
|
||||
val street = it.street.ifEmpty {
|
||||
it.name
|
||||
}
|
||||
|
||||
@@ -107,7 +107,7 @@ class NavigationScreenTest {
|
||||
navigationScreen.navigationType = NavigationType.NAVIGATION
|
||||
|
||||
// Act
|
||||
navigationScreen.calculateNewRoute(Place())
|
||||
navigationScreen.calculateNewRoute(Place(), distance)
|
||||
|
||||
// Assert
|
||||
assertThat(navigationScreen.navigationType).isEqualTo(NavigationType.REROUTE)
|
||||
|
||||
@@ -12,7 +12,7 @@ plugins {
|
||||
|
||||
android {
|
||||
namespace = "com.kouros.data"
|
||||
compileSdk = 36
|
||||
compileSdk = 37
|
||||
|
||||
|
||||
val properties = Properties().apply {
|
||||
|
||||
@@ -129,6 +129,8 @@ object Constants {
|
||||
const val RESTAURANT: String ="restaurant"
|
||||
|
||||
/** The initial location to use as an anchor for searches. */
|
||||
|
||||
val widenmayer = location( 11.595721, 48.146113)
|
||||
val homeVogelhart = location(11.5793748, 48.185749)
|
||||
val homeHohenwaldeck = location( 11.594322, 48.1164817)
|
||||
val ioannina = location( 20.826237, 39.690174)
|
||||
@@ -140,7 +142,7 @@ object Constants {
|
||||
val isarring = location( 11.609696, 48.155116)
|
||||
const val NEXT_STEP_THRESHOLD = 500.0
|
||||
|
||||
const val MAXIMAL_SNAP_CORRECTION = 40.0
|
||||
const val MAXIMAL_SNAP_CORRECTION = 50.0
|
||||
|
||||
const val MAXIMAL_ROUTE_DEVIATION = 100.0
|
||||
|
||||
|
||||
@@ -185,9 +185,7 @@ class NavigationViewModel(private val repository: NavigationRepository) : ViewMo
|
||||
place.id = id
|
||||
id += 1
|
||||
}
|
||||
if (place.distance == 0F || place.distance > 500F) {
|
||||
pl.add(place)
|
||||
}
|
||||
pl.add(place)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user