Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,9 @@ import android.support.test.filters.LargeTest
import android.support.test.rule.ActivityTestRule
import android.support.test.rule.GrantPermissionRule
import android.support.test.runner.AndroidJUnit4
import android.support.v4.content.ContextCompat
import com.mapbox.geojson.Point
import com.mapbox.mapboxsdk.constants.Style
import com.mapbox.mapboxsdk.geometry.LatLng
import com.mapbox.mapboxsdk.maps.MapView
import com.mapbox.mapboxsdk.maps.MapboxMap
import com.mapbox.mapboxsdk.maps.SupportMapFragment
Expand Down Expand Up @@ -154,9 +154,7 @@ class LocationLayerPluginTest {
uiController.loopMainThreadForAtLeast(MAP_CONNECTION_DELAY)

// Check if the puck is visible
val latLng = LatLng(location.latitude, location.longitude)
val point = mapboxMap.projection.toScreenLocation(latLng)
assertThat(mapboxMap.queryRenderedFeatures(point, FOREGROUND_LAYER).isEmpty(), `is`(false))
assertThat(mapboxMap.queryRenderedFeatures(location, FOREGROUND_LAYER).isEmpty(), `is`(false))
}
}
executePluginTest(pluginAction)
Expand Down Expand Up @@ -192,6 +190,119 @@ class LocationLayerPluginTest {
PluginGenerationUtil.getLocationLayerPluginProvider(rule.activity, false, null, options))
}

@Test
fun locationLayerOptions_loadsForegroundBitmapFromNameOption() {
val pluginAction = object : GenericPluginAction.OnPerformGenericPluginAction<LocationLayerPlugin> {
override fun onGenericPluginAction(plugin: LocationLayerPlugin, mapboxMap: MapboxMap,
uiController: UiController, context: Context) {
val foregroundDrawable = ContextCompat.getDrawable(context, R.drawable.ic_media_play)
mapboxMap.addImageFromDrawable("custom-foreground-bitmap", foregroundDrawable!!)
mapboxMap.addImageFromDrawable("custom-background-bitmap", foregroundDrawable)
mapboxMap.addImageFromDrawable("custom-foreground-stale-bitmap", foregroundDrawable)
mapboxMap.addImageFromDrawable("custom-background-stale-bitmap", foregroundDrawable)
mapboxMap.addImageFromDrawable("custom-bearing-bitmap", foregroundDrawable)

plugin.forceLocationUpdate(location)
uiController.loopMainThreadForAtLeast(MAP_CONNECTION_DELAY)
assertThat(mapboxMap.queryRenderedFeatures(location, FOREGROUND_LAYER).isEmpty(), `is`(false))

val feature = mapboxMap.querySourceFeatures(LOCATION_SOURCE)[0]
assertThat(feature.getStringProperty(PROPERTY_FOREGROUND_ICON), `is`(equalTo("custom-foreground-bitmap")))
assertThat(feature.getStringProperty(PROPERTY_BACKGROUND_ICON), `is`(equalTo("custom-background-bitmap")))
assertThat(feature.getStringProperty(PROPERTY_FOREGROUND_STALE_ICON), `is`(equalTo("custom-foreground-stale-bitmap")))
assertThat(feature.getStringProperty(PROPERTY_BACKGROUND_STALE_ICON), `is`(equalTo("custom-background-stale-bitmap")))
assertThat(feature.getStringProperty(PROPERTY_BEARING_ICON), `is`(equalTo("custom-bearing-bitmap")))
}
}

val options = LocationLayerOptions.builder(fragment.activity)
.foregroundName("custom-foreground-bitmap")
.backgroundName("custom-background-bitmap")
.foregroundStaleName("custom-foreground-stale-bitmap")
.backgroundStaleName("custom-background-stale-bitmap")
.bearingName("custom-bearing-bitmap")
.build()
executePluginTest(pluginAction,
PluginGenerationUtil.getLocationLayerPluginProvider(rule.activity, false, null, options))
}

@Test
fun locationLayerOptions_loadsGpsNameWithGpsRenderMode() {
val pluginAction = object : GenericPluginAction.OnPerformGenericPluginAction<LocationLayerPlugin> {
override fun onGenericPluginAction(plugin: LocationLayerPlugin, mapboxMap: MapboxMap,
uiController: UiController, context: Context) {
plugin.renderMode = RenderMode.GPS
uiController.loopMainThreadForAtLeast(MAP_RENDER_DELAY)
val foregroundDrawable = ContextCompat.getDrawable(context, R.drawable.ic_media_play)
mapboxMap.addImageFromDrawable("custom-foreground-bitmap", foregroundDrawable!!)
mapboxMap.addImageFromDrawable("custom-gps-bitmap", foregroundDrawable)

val foregroundId = mapboxMap.querySourceFeatures(LOCATION_SOURCE)[0].getStringProperty(PROPERTY_FOREGROUND_ICON)
assertThat(foregroundId, `is`(equalTo("custom-gps-bitmap")))
}
}

val options = LocationLayerOptions.builder(fragment.activity)
.foregroundName("custom-foreground-bitmap")
.gpsName("custom-gps-bitmap")
.build()
executePluginTest(pluginAction,
PluginGenerationUtil.getLocationLayerPluginProvider(rule.activity, false, null, options))
}

@Test
fun locationLayerOptions_customIconNameRevertsToDefault() {
val pluginAction = object : GenericPluginAction.OnPerformGenericPluginAction<LocationLayerPlugin> {
override fun onGenericPluginAction(plugin: LocationLayerPlugin, mapboxMap: MapboxMap,
uiController: UiController, context: Context) {
plugin.renderMode = RenderMode.GPS
uiController.loopMainThreadForAtLeast(MAP_RENDER_DELAY)

val foregroundId = mapboxMap.querySourceFeatures(LOCATION_SOURCE)[0].getStringProperty(PROPERTY_FOREGROUND_ICON)
assertThat(foregroundId, `is`(equalTo("custom-gps-bitmap")))

plugin.applyStyle(LocationLayerOptions.builder(fragment.activity).build())
uiController.loopMainThreadForAtLeast(MAP_RENDER_DELAY)

val revertedForegroundId = mapboxMap.querySourceFeatures(LOCATION_SOURCE)[0].getStringProperty(PROPERTY_FOREGROUND_ICON)
assertThat(revertedForegroundId, `is`(equalTo(FOREGROUND_ICON)))
}
}

val options = LocationLayerOptions.builder(fragment.activity)
.foregroundName("custom-foreground-bitmap")
.gpsName("custom-gps-bitmap")
.build()
executePluginTest(pluginAction,
PluginGenerationUtil.getLocationLayerPluginProvider(rule.activity, false, null, options))
}

@Test
fun locationLayerOptions_customGpsIconNameChangeBackWithMode() {
val pluginAction = object : GenericPluginAction.OnPerformGenericPluginAction<LocationLayerPlugin> {
override fun onGenericPluginAction(plugin: LocationLayerPlugin, mapboxMap: MapboxMap,
uiController: UiController, context: Context) {
plugin.renderMode = RenderMode.GPS
uiController.loopMainThreadForAtLeast(MAP_RENDER_DELAY)

val foregroundId = mapboxMap.querySourceFeatures(LOCATION_SOURCE)[0].getStringProperty(PROPERTY_FOREGROUND_ICON)
assertThat(foregroundId, `is`(equalTo("custom-gps-bitmap")))

plugin.renderMode = RenderMode.NORMAL
uiController.loopMainThreadForAtLeast(MAP_RENDER_DELAY)

val revertedForegroundId = mapboxMap.querySourceFeatures(LOCATION_SOURCE)[0].getStringProperty(PROPERTY_FOREGROUND_ICON)
assertThat(revertedForegroundId, `is`(equalTo(FOREGROUND_ICON)))
}
}

val options = LocationLayerOptions.builder(fragment.activity)
.gpsName("custom-gps-bitmap")
.build()
executePluginTest(pluginAction,
PluginGenerationUtil.getLocationLayerPluginProvider(rule.activity, false, null, options))
}

@Test
fun stillStaleAfterResuming() {
val pluginAction = object : GenericPluginAction.OnPerformGenericPluginAction<LocationLayerPlugin> {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,14 @@
package com.mapbox.mapboxsdk.plugins.utils

import android.graphics.Bitmap
import android.graphics.Canvas
import android.graphics.drawable.BitmapDrawable
import android.graphics.drawable.Drawable
import android.location.Location
import android.os.Handler
import android.os.Looper
import com.mapbox.geojson.Feature
import com.mapbox.mapboxsdk.geometry.LatLng
import com.mapbox.mapboxsdk.maps.MapboxMap
import com.mapbox.mapboxsdk.style.layers.Property
import com.mapbox.mapboxsdk.style.sources.GeoJsonSource
Expand All @@ -11,6 +17,12 @@ fun MapboxMap.querySourceFeatures(sourceId: String): List<Feature> {
return this.getSourceAs<GeoJsonSource>(sourceId)?.querySourceFeatures(null) as List<Feature>
}

fun MapboxMap.queryRenderedFeatures(location: Location, layerId: String): List<Feature> {
val latLng = LatLng(location.latitude, location.longitude)
val point = this.projection.toScreenLocation(latLng)
return this.queryRenderedFeatures(point, layerId)
}

fun MapboxMap.isLayerVisible(layerId: String): Boolean {
return this.getLayer(layerId)?.visibility?.value?.equals(Property.VISIBLE)!!
}
Expand Down Expand Up @@ -49,4 +61,19 @@ class MapboxTestingUtils {
}
}
}
}

fun MapboxMap.addImageFromDrawable(string: String, drawable: Drawable) {
val bitmapFromDrawable = getBitmapFromDrawable(drawable)
this.addImage(string, bitmapFromDrawable)
}

private fun getBitmapFromDrawable(drawable: Drawable): Bitmap {
if (drawable is BitmapDrawable) return drawable.bitmap
val bitmap = Bitmap.createBitmap(drawable.intrinsicWidth,
drawable.intrinsicHeight, Bitmap.Config.ARGB_8888)
val canvas = Canvas(bitmap)
drawable.setBounds(0, 0, canvas.width, canvas.height)
drawable.draw(canvas)
return bitmap
}
2 changes: 1 addition & 1 deletion app/src/main/res/values/styles.xml
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
<item name="mapbox_foregroundDrawable">@drawable/custom_user_icon</item>

<item name="mapbox_bearingDrawable">@drawable/custom_user_arrow</item>
<item name="mapbox_navigationDrawable">@drawable/custom_user_puck_icon</item>
<item name="mapbox_gpsDrawable">@drawable/custom_user_puck_icon</item>

<item name="mapbox_accuracyAlpha">0.15</item>
<item name="mapbox_accuracyColor">#FF82C6</item>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,13 @@
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_ACCURACY_ALPHA;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_ACCURACY_COLOR;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_ACCURACY_RADIUS;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_BACKGROUND_ICON;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_BACKGROUND_STALE_ICON;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_BEARING_ICON;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_COMPASS_BEARING;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_FOREGROUND_ICON;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_FOREGROUND_ICON_OFFSET;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_FOREGROUND_STALE_ICON;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_GPS_BEARING;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_LOCATION_STALE;
import static com.mapbox.mapboxsdk.plugins.locationlayer.LocationLayerConstants.PROPERTY_SHADOW_ICON_OFFSET;
Expand Down Expand Up @@ -126,6 +131,7 @@ void applyStyle(@NonNull LocationLayerOptions options) {
styleBearing(options);
styleAccuracy(options.accuracyAlpha(), options.accuracyColor());
styleScaling(options);
determineIconsSource(options);
}

void setRenderMode(@RenderMode.Mode int renderMode) {
Expand Down Expand Up @@ -160,6 +166,8 @@ void setRenderMode(@RenderMode.Mode int renderMode) {
default:
break;
}

determineIconsSource(options);
}

int getRenderMode() {
Expand Down Expand Up @@ -217,13 +225,13 @@ private void addSymbolLayer(String layerId, String beforeLayerId) {
iconImage(
match(literal(layerId), literal(""),
stop(FOREGROUND_LAYER, switchCase(
get(PROPERTY_LOCATION_STALE), literal(FOREGROUND_STALE_ICON),
literal(FOREGROUND_ICON))),
get(PROPERTY_LOCATION_STALE), get(PROPERTY_FOREGROUND_STALE_ICON),
get(PROPERTY_FOREGROUND_ICON))),
stop(BACKGROUND_LAYER, switchCase(
get(PROPERTY_LOCATION_STALE), literal(BACKGROUND_STALE_ICON),
literal(BACKGROUND_ICON))),
get(PROPERTY_LOCATION_STALE), get(PROPERTY_BACKGROUND_STALE_ICON),
get(PROPERTY_BACKGROUND_ICON))),
stop(SHADOW_LAYER, literal(SHADOW_ICON)),
stop(BEARING_LAYER, literal(BEARING_ICON))
stop(BEARING_LAYER, get(PROPERTY_BEARING_ICON))
)
),
iconOffset(
Expand Down Expand Up @@ -397,6 +405,29 @@ private void styleScaling(LocationLayerOptions options) {
}
}

private void determineIconsSource(LocationLayerOptions options) {
String foregroundIconString = buildIconString(
renderMode == RenderMode.GPS ? options.gpsName() : options.foregroundName(), FOREGROUND_ICON);
String foregroundStaleIconString = buildIconString(options.foregroundStaleName(), FOREGROUND_STALE_ICON);
String backgroundIconString = buildIconString(options.backgroundName(), BACKGROUND_ICON);
String backgroundStaleIconString = buildIconString(options.backgroundStaleName(), BACKGROUND_STALE_ICON);
String bearingIconString = buildIconString(options.bearingName(), BEARING_ICON);

locationFeature.addStringProperty(PROPERTY_FOREGROUND_ICON, foregroundIconString);
locationFeature.addStringProperty(PROPERTY_BACKGROUND_ICON, backgroundIconString);
locationFeature.addStringProperty(PROPERTY_FOREGROUND_STALE_ICON, foregroundStaleIconString);
locationFeature.addStringProperty(PROPERTY_BACKGROUND_STALE_ICON, backgroundStaleIconString);
locationFeature.addStringProperty(PROPERTY_BEARING_ICON, bearingIconString);
refreshSource();
}

private String buildIconString(@Nullable String bitmapName, @NonNull String drawableName) {
if (bitmapName != null) {
return bitmapName;
}
return drawableName;
}

void setLocationsStale(boolean isStale) {
// If options has stale state disabled, just return here.
if (!options.enableStaleState()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,11 @@ final class LocationLayerConstants {
static final String PROPERTY_ACCURACY_ALPHA = "mapbox-property-accuracy-alpha";
static final String PROPERTY_FOREGROUND_ICON_OFFSET = "mapbox-property-foreground-icon-offset";
static final String PROPERTY_SHADOW_ICON_OFFSET = "mapbox-property-shadow-icon-offset";
static final String PROPERTY_FOREGROUND_ICON = "mapbox-property-foreground-icon";
static final String PROPERTY_BACKGROUND_ICON = "mapbox-property-background-icon";
static final String PROPERTY_FOREGROUND_STALE_ICON = "mapbox-property-foreground-stale-icon";
static final String PROPERTY_BACKGROUND_STALE_ICON = "mapbox-property-background-stale-icon";
static final String PROPERTY_BEARING_ICON = "mapbox-property-shadow-icon";

// Layers
static final String SHADOW_LAYER = "mapbox-location-shadow";
Expand Down
Loading