Skip to content

Commit cd2f573

Browse files
tomaszrybakiewiczabhishek1508
authored andcommitted
Added unit tests for ReplayRouteTripSession
Added unit-tests for NavigationView. Introduced factory methods for components and coordinators created by NavigationView.
1 parent 53f8c17 commit cd2f573

9 files changed

Lines changed: 528 additions & 180 deletions

File tree

libnavui-dropin/src/main/java/com/mapbox/navigation/dropin/NavigationView.kt

Lines changed: 34 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import android.view.LayoutInflater
88
import android.view.View
99
import android.widget.FrameLayout
1010
import androidx.annotation.UiThread
11+
import androidx.annotation.VisibleForTesting
1112
import androidx.core.view.ViewCompat
1213
import androidx.core.view.WindowInsetsCompat
1314
import androidx.fragment.app.Fragment
@@ -22,26 +23,28 @@ import com.mapbox.navigation.base.options.NavigationOptions
2223
import com.mapbox.navigation.core.internal.extensions.attachCreated
2324
import com.mapbox.navigation.core.lifecycle.MapboxNavigationApp
2425
import com.mapbox.navigation.core.replay.MapboxReplayer
25-
import com.mapbox.navigation.dropin.actionbutton.ActionButtonsCoordinator
26-
import com.mapbox.navigation.dropin.analytics.AnalyticsComponent
27-
import com.mapbox.navigation.dropin.backpress.BackPressedComponent
2826
import com.mapbox.navigation.dropin.databinding.MapboxNavigationViewLayoutBinding
29-
import com.mapbox.navigation.dropin.infopanel.InfoPanelCoordinator
27+
import com.mapbox.navigation.dropin.internal.extensions.actionButtonsCoordinator
28+
import com.mapbox.navigation.dropin.internal.extensions.analyticsComponent
29+
import com.mapbox.navigation.dropin.internal.extensions.backPressedComponent
30+
import com.mapbox.navigation.dropin.internal.extensions.infoPanelCoordinator
31+
import com.mapbox.navigation.dropin.internal.extensions.leftFrameCoordinator
32+
import com.mapbox.navigation.dropin.internal.extensions.locationPermissionComponent
33+
import com.mapbox.navigation.dropin.internal.extensions.maneuverCoordinator
34+
import com.mapbox.navigation.dropin.internal.extensions.mapLayoutCoordinator
3035
import com.mapbox.navigation.dropin.internal.extensions.navigationViewAccessToken
36+
import com.mapbox.navigation.dropin.internal.extensions.rightFrameCoordinator
37+
import com.mapbox.navigation.dropin.internal.extensions.roadNameCoordinator
38+
import com.mapbox.navigation.dropin.internal.extensions.scalebarPlaceholderCoordinator
39+
import com.mapbox.navigation.dropin.internal.extensions.speedLimitCoordinator
3140
import com.mapbox.navigation.dropin.internal.extensions.toComponentActivity
3241
import com.mapbox.navigation.dropin.internal.extensions.toViewModelStoreOwner
33-
import com.mapbox.navigation.dropin.maneuver.ManeuverCoordinator
34-
import com.mapbox.navigation.dropin.map.MapLayoutCoordinator
42+
import com.mapbox.navigation.dropin.internal.extensions.tripSessionComponent
3543
import com.mapbox.navigation.dropin.map.MapViewObserver
36-
import com.mapbox.navigation.dropin.map.scalebar.ScalebarPlaceholderCoordinator
3744
import com.mapbox.navigation.dropin.navigationview.MapboxNavigationViewApi
3845
import com.mapbox.navigation.dropin.navigationview.NavigationViewContext
3946
import com.mapbox.navigation.dropin.navigationview.NavigationViewListener
4047
import com.mapbox.navigation.dropin.navigationview.NavigationViewModel
41-
import com.mapbox.navigation.dropin.permission.LocationPermissionComponent
42-
import com.mapbox.navigation.dropin.roadname.RoadNameCoordinator
43-
import com.mapbox.navigation.dropin.speedlimit.SpeedLimitCoordinator
44-
import com.mapbox.navigation.dropin.tripsession.TripSessionComponent
4548
import com.mapbox.navigation.ui.app.internal.SharedApp
4649
import com.mapbox.navigation.ui.base.lifecycle.UIBinder
4750
import com.mapbox.navigation.ui.utils.internal.lifecycle.ViewLifecycleRegistry
@@ -103,7 +106,8 @@ class NavigationView @JvmOverloads constructor(
103106

104107
private val viewModel: NavigationViewModel by lazyViewModel()
105108

106-
private val navigationContext = NavigationViewContext(
109+
@VisibleForTesting
110+
internal val navigationContext = NavigationViewContext(
107111
context = context,
108112
lifecycleOwner = this,
109113
viewModel = viewModel,
@@ -124,30 +128,24 @@ class NavigationView @JvmOverloads constructor(
124128

125129
MapboxNavigationApp.attach(this)
126130

127-
val componentActivity = context.toComponentActivity()
128-
attachCreated(
129-
AnalyticsComponent(),
130-
LocationPermissionComponent(componentActivity, navigationContext.store),
131-
TripSessionComponent(lifecycle, navigationContext.store),
132-
MapLayoutCoordinator(navigationContext, binding),
133-
BackPressedComponent(
134-
componentActivity.onBackPressedDispatcher,
135-
navigationContext.store,
136-
lifecycleOwner = this,
137-
),
138-
ScalebarPlaceholderCoordinator(navigationContext, binding.scalebarLayout),
139-
ManeuverCoordinator(navigationContext, binding.guidanceLayout),
140-
InfoPanelCoordinator(
141-
navigationContext,
142-
binding.infoPanelLayout,
143-
binding.guidelineBottom
144-
),
145-
ActionButtonsCoordinator(navigationContext, binding.actionListLayout),
146-
SpeedLimitCoordinator(navigationContext, binding.speedLimitLayout),
147-
RoadNameCoordinator(navigationContext, binding.roadNameLayout),
148-
LeftFrameCoordinator(navigationContext, binding.emptyLeftContainer),
149-
RightFrameCoordinator(navigationContext, binding.emptyRightContainer)
150-
)
131+
val activity = context.toComponentActivity()
132+
navigationContext.apply {
133+
attachCreated(
134+
analyticsComponent(),
135+
locationPermissionComponent(activity),
136+
tripSessionComponent(),
137+
mapLayoutCoordinator(binding),
138+
backPressedComponent(activity),
139+
scalebarPlaceholderCoordinator(binding.scalebarLayout),
140+
maneuverCoordinator(binding.guidanceLayout),
141+
infoPanelCoordinator(binding.infoPanelLayout, binding.guidelineBottom),
142+
actionButtonsCoordinator(binding.actionListLayout),
143+
speedLimitCoordinator(binding.speedLimitLayout),
144+
roadNameCoordinator(binding.roadNameLayout),
145+
leftFrameCoordinator(binding.emptyLeftContainer),
146+
rightFrameCoordinator(binding.emptyRightContainer)
147+
)
148+
}
151149
}
152150

153151
private fun captureSystemBarsInsets() {

libnavui-dropin/src/main/java/com/mapbox/navigation/dropin/internal/extensions/ContextEx.kt

Lines changed: 4 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -15,18 +15,12 @@ internal tailrec fun Context.recursiveUnwrap(): Context =
1515
this
1616
}
1717

18-
internal fun Context.toViewModelStoreOwner(): ViewModelStoreOwner {
19-
val viewModelStoreOwner = this.recursiveUnwrap() as? ViewModelStoreOwner
20-
checkNotNull(viewModelStoreOwner) {
18+
internal fun Context.toViewModelStoreOwner(): ViewModelStoreOwner =
19+
checkNotNull(this.recursiveUnwrap() as? ViewModelStoreOwner) {
2120
"Please ensure that the hosting Context is a valid ViewModelStoreOwner"
2221
}
23-
return viewModelStoreOwner
24-
}
2522

26-
internal fun Context.toComponentActivity(): ComponentActivity {
27-
val componentActivity = this.recursiveUnwrap() as? ComponentActivity
28-
checkNotNull(componentActivity) {
23+
internal fun Context.toComponentActivity(): ComponentActivity =
24+
checkNotNull(this.recursiveUnwrap() as? ComponentActivity) {
2925
"Please ensure that the hosting Context is a valid ComponentActivity"
3026
}
31-
return componentActivity
32-
}

libnavui-dropin/src/main/java/com/mapbox/navigation/dropin/internal/extensions/MapboxExtendableButtonEx.kt

Lines changed: 0 additions & 28 deletions
This file was deleted.

libnavui-dropin/src/main/java/com/mapbox/navigation/dropin/internal/extensions/NavigationViewContextEx.kt

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,23 +3,43 @@
33
package com.mapbox.navigation.dropin.internal.extensions
44

55
import android.view.ViewGroup
6+
import androidx.activity.ComponentActivity
67
import androidx.annotation.Px
8+
import androidx.constraintlayout.widget.Guideline
79
import com.mapbox.navigation.base.ExperimentalPreviewMapboxNavigationAPI
810
import com.mapbox.navigation.core.lifecycle.MapboxNavigationObserver
911
import com.mapbox.navigation.dropin.EmptyBinder
12+
import com.mapbox.navigation.dropin.LeftFrameCoordinator
13+
import com.mapbox.navigation.dropin.RightFrameCoordinator
14+
import com.mapbox.navigation.dropin.actionbutton.ActionButtonsCoordinator
1015
import com.mapbox.navigation.dropin.actionbutton.AudioGuidanceButtonBinder
1116
import com.mapbox.navigation.dropin.actionbutton.CameraModeButtonBinder
1217
import com.mapbox.navigation.dropin.actionbutton.CompassButtonBinder
1318
import com.mapbox.navigation.dropin.actionbutton.RecenterButtonBinder
19+
import com.mapbox.navigation.dropin.analytics.AnalyticsComponent
20+
import com.mapbox.navigation.dropin.backpress.BackPressedComponent
21+
import com.mapbox.navigation.dropin.databinding.MapboxNavigationViewLayoutBinding
1422
import com.mapbox.navigation.dropin.infopanel.InfoPanelArrivalTextBinder
23+
import com.mapbox.navigation.dropin.infopanel.InfoPanelCoordinator
1524
import com.mapbox.navigation.dropin.infopanel.InfoPanelEndNavigationButtonBinder
1625
import com.mapbox.navigation.dropin.infopanel.InfoPanelPoiNameBinder
1726
import com.mapbox.navigation.dropin.infopanel.InfoPanelRoutePreviewButtonBinder
1827
import com.mapbox.navigation.dropin.infopanel.InfoPanelStartNavigationButtonBinder
28+
import com.mapbox.navigation.dropin.maneuver.ManeuverCoordinator
29+
import com.mapbox.navigation.dropin.map.MapLayoutCoordinator
30+
import com.mapbox.navigation.dropin.map.scalebar.ScalebarPlaceholderCoordinator
1931
import com.mapbox.navigation.dropin.navigationview.NavigationViewContext
32+
import com.mapbox.navigation.dropin.permission.LocationPermissionComponent
33+
import com.mapbox.navigation.dropin.roadname.RoadNameCoordinator
34+
import com.mapbox.navigation.dropin.speedlimit.SpeedLimitCoordinator
2035
import com.mapbox.navigation.dropin.tripprogress.TripProgressBinder
36+
import com.mapbox.navigation.dropin.tripsession.TripSessionComponent
2137
import kotlinx.coroutines.flow.combine
2238

39+
//
40+
// Components
41+
//
42+
2343
@ExperimentalPreviewMapboxNavigationAPI
2444
internal fun NavigationViewContext.poiNameComponent(
2545
viewGroup: ViewGroup
@@ -193,3 +213,62 @@ internal fun NavigationViewContext.recenterButtonComponent(
193213
}
194214
return reloadOnChange(binderFlow) { it.bind(buttonContainer) }
195215
}
216+
217+
@ExperimentalPreviewMapboxNavigationAPI
218+
internal fun NavigationViewContext.analyticsComponent() =
219+
AnalyticsComponent()
220+
221+
@ExperimentalPreviewMapboxNavigationAPI
222+
internal fun NavigationViewContext.locationPermissionComponent(activity: ComponentActivity) =
223+
LocationPermissionComponent(activity, store)
224+
225+
@ExperimentalPreviewMapboxNavigationAPI
226+
internal fun NavigationViewContext.tripSessionComponent() =
227+
TripSessionComponent(lifecycleOwner.lifecycle, store)
228+
229+
@ExperimentalPreviewMapboxNavigationAPI
230+
internal fun NavigationViewContext.backPressedComponent(activity: ComponentActivity) =
231+
BackPressedComponent(activity.onBackPressedDispatcher, store, lifecycleOwner)
232+
233+
//
234+
// Coordinators
235+
//
236+
237+
@ExperimentalPreviewMapboxNavigationAPI
238+
internal fun NavigationViewContext.mapLayoutCoordinator(
239+
binding: MapboxNavigationViewLayoutBinding
240+
) = MapLayoutCoordinator(this, binding)
241+
242+
@ExperimentalPreviewMapboxNavigationAPI
243+
internal fun NavigationViewContext.scalebarPlaceholderCoordinator(scalebarLayout: ViewGroup) =
244+
ScalebarPlaceholderCoordinator(this, scalebarLayout)
245+
246+
@ExperimentalPreviewMapboxNavigationAPI
247+
internal fun NavigationViewContext.maneuverCoordinator(guidanceLayout: ViewGroup) =
248+
ManeuverCoordinator(this, guidanceLayout)
249+
250+
@ExperimentalPreviewMapboxNavigationAPI
251+
internal fun NavigationViewContext.infoPanelCoordinator(
252+
infoPanelLayout: ViewGroup,
253+
guidelineBottom: Guideline
254+
) = InfoPanelCoordinator(this, infoPanelLayout, guidelineBottom)
255+
256+
@ExperimentalPreviewMapboxNavigationAPI
257+
internal fun NavigationViewContext.actionButtonsCoordinator(actionListLayout: ViewGroup) =
258+
ActionButtonsCoordinator(this, actionListLayout)
259+
260+
@ExperimentalPreviewMapboxNavigationAPI
261+
internal fun NavigationViewContext.speedLimitCoordinator(speedLimitLayout: ViewGroup) =
262+
SpeedLimitCoordinator(this, speedLimitLayout)
263+
264+
@ExperimentalPreviewMapboxNavigationAPI
265+
internal fun NavigationViewContext.roadNameCoordinator(roadNameLayout: ViewGroup) =
266+
RoadNameCoordinator(this, roadNameLayout)
267+
268+
@ExperimentalPreviewMapboxNavigationAPI
269+
internal fun NavigationViewContext.leftFrameCoordinator(emptyLeftContainer: ViewGroup) =
270+
LeftFrameCoordinator(this, emptyLeftContainer)
271+
272+
@ExperimentalPreviewMapboxNavigationAPI
273+
internal fun NavigationViewContext.rightFrameCoordinator(emptyRightContainer: ViewGroup) =
274+
RightFrameCoordinator(this, emptyRightContainer)

libnavui-dropin/src/main/java/com/mapbox/navigation/dropin/map/MapViewOwner.kt

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
package com.mapbox.navigation.dropin.map
22

3+
import androidx.annotation.VisibleForTesting
34
import com.mapbox.maps.MapView
45
import com.mapbox.navigation.base.ExperimentalPreviewMapboxNavigationAPI
56
import kotlinx.coroutines.flow.MutableStateFlow
@@ -14,20 +15,20 @@ internal class MapViewOwner {
1415
field = value
1516
_mapViews.value = value
1617
}
17-
private val listeners = CopyOnWriteArraySet<MapViewObserver>()
18+
private val observers = CopyOnWriteArraySet<MapViewObserver>()
1819
private val _mapViews = MutableStateFlow(mapView)
1920
val mapViews = _mapViews.asStateFlow()
2021

2122
fun registerObserver(observer: MapViewObserver) {
22-
if (listeners.add(observer)) {
23+
if (observers.add(observer)) {
2324
mapView?.let {
2425
observer.onAttached(it)
2526
}
2627
}
2728
}
2829

2930
fun unregisterObserver(observer: MapViewObserver) {
30-
if (listeners.remove(observer)) {
31+
if (observers.remove(observer)) {
3132
mapView?.let {
3233
observer.onDetached(it)
3334
}
@@ -36,15 +37,18 @@ internal class MapViewOwner {
3637

3738
fun updateMapView(mapView: MapView?) {
3839
this.mapView?.let {
39-
listeners.forEach { listener ->
40+
observers.forEach { listener ->
4041
listener.onDetached(it)
4142
}
4243
}
4344
this.mapView = mapView
4445
mapView?.let {
45-
listeners.forEach { listener ->
46+
observers.forEach { listener ->
4647
listener.onAttached(it)
4748
}
4849
}
4950
}
51+
52+
@VisibleForTesting
53+
internal fun getRegisteredObservers() = observers.toSet()
5054
}

0 commit comments

Comments
 (0)