Inset map
Show a smaller inset map fragment and link it to a larger map for two map interaction.
<?xml version="1.0" encoding="utf-8"?><FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:mapbox="http://schemas.android.com/apk/res-auto"android:layout_width="match_parent"android:layout_height="match_parent"> <com.mapbox.maps.MapViewandroid:id="@+id/mapView"android:layout_width="match_parent"android:layout_height="match_parent"mapbox:mapbox_cameraTargetLat="11.302318"mapbox:mapbox_cameraTargetLng="106.025839"mapbox:mapbox_cameraZoom="5.11" /> <androidx.cardview.widget.CardViewandroid:id="@+id/cardview"android:layout_width="150dp"android:layout_height="150dp"android:layout_gravity="bottom|end"android:layout_marginEnd="16dp"android:layout_marginBottom="90dp"> <FrameLayoutandroid:id="@+id/mini_map_fragment_container"android:layout_width="match_parent"android:layout_height="match_parent" /> </androidx.cardview.widget.CardView> <com.google.android.material.floatingactionbutton.FloatingActionButtonandroid:id="@+id/show_bounds_toggle_fab"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="end|bottom"android:layout_marginEnd="16dp"android:layout_marginBottom="16dp"android:src="@drawable/ic_swap_horiz_white_24dp" /> </FrameLayout>
package com.mapbox.maps.testapp.examples import android.graphics.Colorimport android.os.Bundleimport androidx.appcompat.app.AppCompatActivityimport com.mapbox.geojson.Featureimport com.mapbox.geojson.LineStringimport com.mapbox.geojson.Pointimport com.mapbox.maps.*import com.mapbox.maps.extension.observable.eventdata.CameraChangedEventDataimport com.mapbox.maps.extension.style.layers.addLayerimport com.mapbox.maps.extension.style.layers.generated.lineLayerimport com.mapbox.maps.extension.style.layers.getLayerimport com.mapbox.maps.extension.style.layers.properties.generated.LineCapimport com.mapbox.maps.extension.style.layers.properties.generated.LineJoinimport com.mapbox.maps.extension.style.layers.properties.generated.Visibilityimport com.mapbox.maps.extension.style.sources.addSourceimport com.mapbox.maps.extension.style.sources.generated.GeoJsonSourceimport com.mapbox.maps.extension.style.sources.generated.geoJsonSourceimport com.mapbox.maps.extension.style.sources.getSourceimport com.mapbox.maps.plugin.attribution.attributionimport com.mapbox.maps.plugin.compass.compassimport com.mapbox.maps.plugin.delegates.listeners.OnCameraChangeListenerimport com.mapbox.maps.plugin.gestures.gesturesimport com.mapbox.maps.plugin.logo.logoimport com.mapbox.maps.plugin.scalebar.scalebarimport com.mapbox.maps.testapp.Rimport com.mapbox.maps.testapp.databinding.ActivityInsetMapBindingimport com.mapbox.maps.testapp.examples.fragment.MapFragment /*** Example demonstrating displaying two maps: main map and small map with lower zoom* in bottom-right corner with optional bounds showing what area is covered by main map.*/class InsetMapActivity : AppCompatActivity(), OnCameraChangeListener { private lateinit var mainMapboxMap: MapboxMapprivate var insetMapboxMap: MapboxMap? = null override fun onCreate(savedInstanceState: Bundle?) {super.onCreate(savedInstanceState)val binding = ActivityInsetMapBinding.inflate(layoutInflater)setContentView(binding.root)mainMapboxMap = binding.mapView.getMapboxMap()mainMapboxMap.loadStyleUri(styleUri = STYLE_URL) { mainMapboxMap.addOnCameraChangeListener(this@InsetMapActivity) } var insetMapFragment: MapFragment? =supportFragmentManager.findFragmentByTag(INSET_FRAGMENT_TAG) as? MapFragmentif (insetMapFragment == null) {// Create fragment transaction for the inset fragmentval transaction = supportFragmentManager.beginTransaction()insetMapFragment = MapFragment()// Add fragmentMap fragment to parent containertransaction.add(R.id.mini_map_fragment_container, insetMapFragment, INSET_FRAGMENT_TAG)transaction.commit()}setInsetMapStyle(insetMapFragment) binding.showBoundsToggleFab.setOnClickListener {// Toggle the visibility of the camera bounds LineLayerinsetMapboxMap?.getStyle { style ->style.getLayer(BOUNDS_LINE_LAYER_LAYER_ID)?.apply {visibility(if (visibility == Visibility.VISIBLE) Visibility.NONE else Visibility.VISIBLE)}}}} private fun setInsetMapStyle(insetMapFragment: MapFragment) {insetMapFragment.getMapAsync {insetMapboxMap = itinsetMapboxMap?.loadStyleUri(styleUri = STYLE_URL) { style ->val source = geoJsonSource(BOUNDS_LINE_LAYER_SOURCE_ID) {feature(Feature.fromGeometry(LineString.fromLngLats(getRectanglePoints())))}style.addSource(source) // The layer properties for our line. This is where we make the line dotted, set the color, etc.val layer = lineLayer(BOUNDS_LINE_LAYER_LAYER_ID, BOUNDS_LINE_LAYER_SOURCE_ID) {lineCap(LineCap.ROUND)lineJoin(LineJoin.ROUND)lineWidth(3.0)lineColor(Color.YELLOW)visibility(Visibility.VISIBLE)}style.addLayer(layer)updateInsetMapLineLayerBounds(style)}insetMapFragment.getMapView()?.apply {logo.enabled = falsescalebar.enabled = falseattribution.enabled = falsecompass.enabled = false gestures.updateSettings {scrollEnabled = falsepinchToZoomEnabled = false}}}} override fun onCameraChanged(eventData: CameraChangedEventData) {val mainCameraPosition = mainMapboxMap.cameraStateval insetCameraPosition = CameraOptions.Builder().zoom(mainCameraPosition.zoom.minus(ZOOM_DISTANCE_BETWEEN_MAIN_AND_INSET_MAPS)).pitch(mainCameraPosition.pitch).bearing(mainCameraPosition.bearing).center(mainCameraPosition.center).build()insetMapboxMap?.setCamera(insetCameraPosition)insetMapboxMap?.getStyle { style -> updateInsetMapLineLayerBounds(style) }} private fun updateInsetMapLineLayerBounds(fullyLoadedStyle: Style) {(fullyLoadedStyle.getSource(BOUNDS_LINE_LAYER_SOURCE_ID) as? GeoJsonSource)?.apply {feature(Feature.fromGeometry(LineString.fromLngLats(getRectanglePoints())))}} private fun getRectanglePoints(): List<Point> {val bounds = mainMapboxMap.coordinateBoundsForCamera(mainMapboxMap.cameraState.toCameraOptions())return listOf(Point.fromLngLat(bounds.northeast.longitude(), bounds.northeast.latitude()),Point.fromLngLat(bounds.northeast.longitude(), bounds.southwest.latitude()),Point.fromLngLat(bounds.southwest.longitude(), bounds.southwest.latitude()),Point.fromLngLat(bounds.southwest.longitude(), bounds.northeast.latitude()),Point.fromLngLat(bounds.northeast.longitude(), bounds.northeast.latitude()))} companion object {private const val STYLE_URL = "mapbox://styles/mapbox/cj5l80zrp29942rmtg0zctjto"private const val INSET_FRAGMENT_TAG = "com.mapbox.insetMapFragment"private const val BOUNDS_LINE_LAYER_SOURCE_ID = "BOUNDS_LINE_LAYER_SOURCE_ID"private const val BOUNDS_LINE_LAYER_LAYER_ID = "BOUNDS_LINE_LAYER_LAYER_ID"private const val ZOOM_DISTANCE_BETWEEN_MAIN_AND_INSET_MAPS = 3}}