+
+- :material-clock-fast:{ .lg .middle } __Quickstart__
+
+ ---
+
+ Learn how to include MapLibre Android in your project
+
+ [:octicons-arrow-right-24: Getting started](getting-started.md)
+
+- :fontawesome-brands-slack:{ .lg .middle } __Find us on Slack__
+
+ ---
+
+ Discuss the project and ask questions in the `#maplibre-android` channel
+
+ [:octicons-arrow-right-24: Slack](https://osmus.slack.com/archives/C01G3D28DAB)
+
+- :fontawesome-solid-code:{ .lg .middle } __Contribute to these Docs__
+
+ ---
+
+ Share your own examples with the community!
+
+ [:octicons-arrow-right-24: Documentation on GitHub](https://github.com/maplibre/maplibre-native/tree/main/platform/android/docs)
+
+
+
+
+## Open-Source Apps Using MapLibre Android
+
+You can learn how to use the API from MapLibre Android by stuying the source code of existing apps that intergrate MapLibre Android. Here are some open-source apps that use MapLibre Android:
+
+- [Streetcomplete](https://github.com/streetcomplete/StreetComplete) ([source code](https://github.com/search?q=repo%3Astreetcomplete%2FStreetComplete%20maplibre&type=code))
+- [The official Wikipedia app for Android](https://github.com/wikimedia/apps-android-wikipedia) ([source code](https://github.com/search?q=repo%3Awikimedia%2Fapps-android-wikipedia%20maplibre&type=code)).
+- [MapLibreAndroidTestApp](https://github.com/maplibre/maplibre-native/tree/main/platform/android/MapLibreAndroidTestApp). This app is part of the MapLibre Native repository and is used for (automated) testing. Many of the examples in this documentation site come directly from this app.
+
+## See Also
+
+- [MapLibre Android API Documentation](https://maplibre.org/maplibre-native/android/api/)
+- [Source code on GitHub](https://github.com/maplibre/maplibre-native/tree/main/platform/android)
+- [Latest releases](https://github.com/maplibre/maplibre-native/releases?q=android-v11&expanded=true)
+- [GitHub Discussions](https://github.com/maplibre/maplibre-native/discussions/categories/q-a?discussions_q=is%3Aopen+category%3AQ%26A+label%3Aandroid)
+- [MapLibre on Slack](https://slack.openstreetmap.us). Join the `#maplibre-native` and `#maplibre-android` channels.
\ No newline at end of file
diff --git a/platform/android/docs/annotations/add-markers.md b/platform/android/docs/annotations/add-markers.md
new file mode 100644
index 00000000000..bfa255a9301
--- /dev/null
+++ b/platform/android/docs/annotations/add-markers.md
@@ -0,0 +1,13 @@
+# Add Markers in Bulk
+
+This example demonstrates how you can add markers in bulk.
+
+
+
+
+
+
+
+```kotlin title="BulkMarkerActivity.kt"
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/BulkMarkerActivity.kt"
+```
\ No newline at end of file
diff --git a/docs/mdbook/src/android/annotation-guide.md b/platform/android/docs/annotations/marker-annotations.md
similarity index 77%
rename from docs/mdbook/src/android/annotation-guide.md
rename to platform/android/docs/annotations/marker-annotations.md
index e21eee1b280..a094e94d35f 100644
--- a/docs/mdbook/src/android/annotation-guide.md
+++ b/platform/android/docs/annotations/marker-annotations.md
@@ -4,6 +4,7 @@ This guide will show you how to add Markers in the map.
`Annotation` is an overlay on top of a Map. In package
`org.maplibre.android.annotations`, it has the following subclasses:
+
1. [Marker]
2. [Polyline]
3. [Polygon]
@@ -23,50 +24,44 @@ rename Activity into `JsonApiActivity`,
and pull the GeoJSON data from a free and public API.
Then add markers to the map with GeoJSON:
-1. In your module Gradle file (usually `//build.gradle`), add
- `okhttp` to simplify code for making HTTP requests.
-
- ```gradle
- dependencies {
- ...
- implementation 'com.squareup.okhttp3:okhttp:4.10.0'
- ...
- }
- ```
+1. In your module Gradle file (usually `//build.gradle`), add `okhttp` to simplify code for making HTTP requests.
+ ```gradle
+ dependencies {
+ ...
+ implementation 'com.squareup.okhttp3:okhttp:4.10.0'
+ ...
+ }
+ ```
2. Sync your Android project the with Gradle files.
-3. In `JsonApiActivity` we add a new variable for `MapboxMap`.
+3. In `JsonApiActivity` we add a new variable for `MapLibreMap`.
It is used to add annotations to the map instance.
+ ```kotlin
+ --8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:top"
+ ```
-```kotlin
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:top}}
-```
-
-4. Call `mapview.getMapSync()` in order to get a `MapboxMap` object.
+4. Call `mapview.getMapSync()` in order to get a `MapLibreMap` object.
After `maplibreMap` is assigned, call the `getEarthQuakeDataFromUSGS()` method
to make a HTTP request and transform data into the map annotations.
-
-```kotlin
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:mapAsync}}
-```
+ ```kotlin
+ --8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:mapAsync"
+ ```
5. Define a function `getEarthQuakeDataFromUSGS()` to fetch GeoJSON data from a public API.
If we successfully get the response, call `addMarkersToMap()` on the UI thread.
-
-```kotlin
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:getEarthquakes}}
-```
+ ```kotlin
+ --8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:getEarthquakes"
+ ```
6. Now it is time to add markers into the map.
- In the `addMarkersToMap()` method, we define two types of bitmap for the marker icon.
- For each feature in the GeoJSON, add a marker with a snippet about earthquake details.
- If the magnitude of an earthquake is bigger than 6.0, we use the red icon. Otherwise, we use the blue one.
- Finally, move the camera to the bounds of the newly added markers
-
-```kotlin
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:addMarkers}}
-```
+ ```kotlin
+ --8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/annotation/JsonApiActivity.kt:addMarkers"
+ ```
7. Here is the final result. For the full contents of `JsonApiActivity`, please visit source code of our [Test App].
@@ -81,7 +76,7 @@ Then add markers to the map with GeoJSON:
[marker image]: https://raw.githubusercontent.com/maplibre/maplibre-native/main/test/fixtures/sprites/default_marker.png
[IconFactory]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.annotations/-icon-factory/index.html
[Icon]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.annotations/-icon/index.html
-[Quickstart]: ./getting-started-guide.md
+[Quickstart]: ../getting-started.md
[mvn]: https://mvnrepository.com/artifact/org.maplibre.gl/android-plugin-annotation-v9
[Android Developer Documentation]: https://developer.android.com/topic/libraries/architecture/coroutines
[MarkerOptions]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.annotations/-marker-options/index.html
diff --git a/platform/android/docs/assets/extra.css b/platform/android/docs/assets/extra.css
new file mode 100644
index 00000000000..a7be243b3d9
--- /dev/null
+++ b/platform/android/docs/assets/extra.css
@@ -0,0 +1,18 @@
+
+[data-md-color-scheme="default"] {
+ --md-primary-fg-color: #295DAA;
+ --md-accent-fg-color: #568ad6;
+}
+
+[data-md-color-scheme="slate"] {
+ --md-primary-fg-color: #295DAA;
+ --md-accent-fg-color: #568ad6;
+}
+
+.md-nav__title {
+ display: none;
+}
+
+.md-grid {
+ max-width: 1800px;
+}
\ No newline at end of file
diff --git a/platform/android/docs/assets/logo.svg b/platform/android/docs/assets/logo.svg
new file mode 100644
index 00000000000..fa409227a77
--- /dev/null
+++ b/platform/android/docs/assets/logo.svg
@@ -0,0 +1,62 @@
+
+
+
+
diff --git a/platform/android/docs/camera/animation-types.md b/platform/android/docs/camera/animation-types.md
new file mode 100644
index 00000000000..4c08acac3da
--- /dev/null
+++ b/platform/android/docs/camera/animation-types.md
@@ -0,0 +1,13 @@
+# Animation Types
+
+This example showcases the different animation types.
+
+- **Move**: available via the `MapLibreMap.moveCamera` method.
+- **Ease**: available via the `MapLibreMap.easeCamera` method.
+- **Animate**: available via the `MapLibreMap.animateCamera` method.
+
+It also shows how to pass callbacks that are called when an animation is cancelled.
+
+```kotlin title="CameraAnimationTypeActivity.kt"
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/camera/CameraAnimationTypeActivity.kt"
+```
diff --git a/platform/android/docs/camera/animator-animation.md b/platform/android/docs/camera/animator-animation.md
new file mode 100644
index 00000000000..eb8029c7cfd
--- /dev/null
+++ b/platform/android/docs/camera/animator-animation.md
@@ -0,0 +1,7 @@
+# Animator Animation
+
+This example showcases how to use the Animator API to schedule a sequence of map animations.
+
+```kotlin title="CameraAnimatorActivity.kt"
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/camera/CameraAnimatorActivity.kt"
+```
\ No newline at end of file
diff --git a/platform/android/docs/camera/cameraposition.md b/platform/android/docs/camera/cameraposition.md
new file mode 100644
index 00000000000..e4a22c75589
--- /dev/null
+++ b/platform/android/docs/camera/cameraposition.md
@@ -0,0 +1,7 @@
+# CameraPosition Capabilities
+
+This example showcases how to listen to camera change events.
+
+```kotlin title="CameraPositionActivity.kt"
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/camera/CameraPositionActivity.kt"
+```
\ No newline at end of file
diff --git a/platform/android/docs/camera/gesture-detector.md b/platform/android/docs/camera/gesture-detector.md
new file mode 100644
index 00000000000..16aff9f7886
--- /dev/null
+++ b/platform/android/docs/camera/gesture-detector.md
@@ -0,0 +1,28 @@
+# Gesture Detector
+
+The gesture detector of MapLibre Android is encapsulated in the [`maplibre-gestures-android`](https://github.com/maplibre/maplibre-gestures-android) package.
+
+#### Gesture Listeners
+
+You can add listeners for move, rotate, scale and shove gestures. For example, adding a move gesture listener with `MapLibreMap.addOnRotateListener`:
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/camera/GestureDetectorActivity.kt:addOnMoveListener"
+```
+
+Refer to the full example below for examples of listeners for the other gesture types.
+
+#### Settings
+
+You can access an `UISettings` object via `MapLibreMap.uiSettings`. Available settings include:
+
+- **Toggle Quick Zoom**. You can double tap on the map to use quick zoom. You can toggle this behavior on and off (`UiSettings.isQuickZoomGesturesEnabled`).
+- **Toggle Velocity Animations**. By default flicking causes the map to continue panning (while decelerating). You can turn this off with `UiSettings.isScaleVelocityAnimationEnabled`.
+- **Toggle Rotate Enabled**. Use `uiSettings.isRotateGesturesEnabled`.
+- **Toggle Zoom Enabled**. Use `uiSettings.isZoomGesturesEnabled`.
+
+## Full Example Activity
+
+```kotlin title="GestureDetectorActivity.kt"
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/camera/GestureDetectorActivity.kt"
+```
\ No newline at end of file
diff --git a/platform/android/docs/camera/lat-lng-bounds.md b/platform/android/docs/camera/lat-lng-bounds.md
new file mode 100644
index 00000000000..4aaa94d62fa
--- /dev/null
+++ b/platform/android/docs/camera/lat-lng-bounds.md
@@ -0,0 +1,26 @@
+# LatLngBounds API
+
+
+!!! note
+
+ You can find the full source code of this example in [`LatLngBoundsActivity.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/testapp/activity/camera/LatLngBoundsActivity.kt) of the MapLibreAndroidTestApp.
+
+This example demonstrates setting the camera to some bounds defined by some features. It sets these bounds when the map is initialized and when the [bottom sheet](https://m2.material.io/components/sheets-bottom) is opened or closed.
+
+
+
+Here you can see how the feature collection is loaded and how `MapLibreMap.getCameraForLatLngBounds` is used to set the bounds during map initialization:
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/camera/LatLngBoundsActivity.kt:featureCollection"
+```
+
+The `createBounds` function uses the `LatLngBounds` API to include all points within the bounds:
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/camera/LatLngBoundsActivity.kt:createBounds"
+```
\ No newline at end of file
diff --git a/docs/mdbook/src/android/map-options-guide.md b/platform/android/docs/configuration.md
similarity index 85%
rename from docs/mdbook/src/android/map-options-guide.md
rename to platform/android/docs/configuration.md
index c3fdc5b162e..01126e8cf81 100644
--- a/docs/mdbook/src/android/map-options-guide.md
+++ b/platform/android/docs/configuration.md
@@ -1,4 +1,4 @@
-# MapLibre Configuration
+# Configuration
This guide will explain various ways to create a map.
@@ -13,6 +13,7 @@ There are several ways to build a `MapView`:
Before diving into `MapView` configurations, let's understand the capabilities of both XML namespaces and `MapLibreMapOptions`.
Here are some common configurations you can set:
+
- Map base URI
- Camera settings
- Zoom level
@@ -30,7 +31,7 @@ We will explore how to achieve these configurations in XML layout and programmat
To configure `MapView` within an XML layout, you need to use the right namespace and provide the necessary data in the layout file.
```xml
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/res/layout/activity_map_options_xml.xml}}
+--8<-- "MapLibreAndroidTestApp/src/main/res/layout/activity_map_options_xml.xml"
```
This can be found in [`activity_map_options_xml.xml`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/res/layout/activity_map_fragment.xml).
@@ -38,7 +39,7 @@ This can be found in [`activity_map_options_xml.xml`](https://github.com/maplibr
You can assign any other existing values to the `maplibre...` tags. Then, you only need to create `MapView` and `MapLibreMap` objects with a simple setup in the Activity.
```kotlin
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/options/MapOptionsXmlActivity.kt}}
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/options/MapOptionsXmlActivity.kt"
```
This can be found in [`MapOptionsXmlActivity.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/options/MapOptionsXmlActivity.kt).
@@ -47,7 +48,7 @@ This can be found in [`MapOptionsXmlActivity.kt`](https://github.com/maplibre/ma
Here we don't have to create MapView from XML since we want to create it programmatically.
```xml
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/res/layout/activity_map_options_xml.xml}}
+--8<-- "MapLibreAndroidTestApp/src/main/res/layout/activity_map_options_runtime.xml"
```
This can be found in [`activity_map_options_runtime.xml`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/res/layout/activity_map_options_runtime.xml).
@@ -55,7 +56,7 @@ This can be found in [`activity_map_options_runtime.xml`](https://github.com/map
A `MapLibreMapOptions` object must be created and passed to the MapView constructor. All setup is done in the Activity code:
```kotlin
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/options/MapOptionsRuntimeActivity.kt}}
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/options/MapOptionsRuntimeActivity.ktl"
```
This can be found in [`MapOptionsRuntimeActivity.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/options/MapOptionsRuntimeActivity.kt).
@@ -77,7 +78,7 @@ If you are using MapFragment in your project, it is also easy to provide initial
Let's see how this can be done in a sample activity:
```kotlin
-{{#include ../../../../platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/fragment/SupportMapFragmentActivity.kt}}
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/fragment/SupportMapFragmentActivity.kt"
```
You can also find the full contents of `SupportMapFragmentActivity` in the [MapLibreAndroidTestApp](https://github.com/maplibre/maplibre-native/tree/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/fragment/SupportMapFragmentActivity.kt).
diff --git a/docs/mdbook/src/android/getting-started-guide.md b/platform/android/docs/getting-started.md
similarity index 83%
rename from docs/mdbook/src/android/getting-started-guide.md
rename to platform/android/docs/getting-started.md
index 6ff8114bc81..9e05c22334b 100644
--- a/docs/mdbook/src/android/getting-started-guide.md
+++ b/platform/android/docs/getting-started.md
@@ -1,11 +1,5 @@
# Quickstart
-
-
-In versions prior to the (upcoming) MapLibre Native for Android 11.0 release, you need to use `com.mapbox.mapboxsdk.*` for imports instead of `org.maplibre.android.*`. Classes with `Mapbox` in the name are replaced with `MapLibre`. Details can be found in the [changelog](https://github.com/maplibre/maplibre-native/blob/main/platform/android/CHANGELOG.md).
-
-
-
1. Add bintray Maven repositories to your project-level Gradle file (usually `//build.gradle`).
```gradle
@@ -17,7 +11,7 @@ In versions prior to the (upcoming) MapLibre Native for Android 11.0 release, yo
}
```
-2. Add the library as a dependency into your module Gradle file (usually `//build.gradle`). Replace `` with the latest MapLibre Native version (e.g.: `org.maplibre.gl:android-sdk:10.0.2`). Visit [https://mvnrepository.com/artifact/org.maplibre.gl/android-sdk](https://mvnrepository.com/artifact/org.maplibre.gl/android-sdk) to view the version history of MapLibre Native for android.
+2. Add the library as a dependency into your module Gradle file (usually `//build.gradle`). Replace `` with the [latest MapLibre Android version](https://github.com/maplibre/maplibre-native/releases?q=android-v11&expanded=true) (e.g.: `org.maplibre.gl:android-sdk:11.5.2`):
```gradle
dependencies {
@@ -115,6 +109,7 @@ In versions prior to the (upcoming) MapLibre Native for Android 11.0 release, yo
```
6. Build and run the app. If you run the app successfully, a map will be displayed as seen in the screenshot below.
+
diff --git a/platform/android/docs/location-component.md b/platform/android/docs/location-component.md
new file mode 100644
index 00000000000..bedaa24404b
--- /dev/null
+++ b/platform/android/docs/location-component.md
@@ -0,0 +1,95 @@
+# LocationComponent
+
+This guide will demonstrate how to utilize the [LocationComponent] to represent the user's current location.
+
+
+When implementing the [LocationComponent], the application should request location permissions. Declare the need for foreground location in the `AndroidManifest.xml` file. For more information, please refer to the [Android Developer Documentation].
+
+```xml
+
+
+
+
+
+
+
+```
+
+Create a new activity named `BasicLocationPulsingCircleActivity`:
+
+- This Activity should implement the `OnMapReadyCallback` interface. The `onMapReady()` method is triggered when the map is ready to be used.
+- Add a variable `permissionsManager` to manage permissions.
+- Add a variable `locationComponent` to manage user location.
+- At the end of the `onCreate()` method, call `checkPermissions()` to ensure that the application can access the user's location.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/location/BasicLocationPulsingCircleActivity.kt:top"
+```
+
+In the `checkPermissions()` method, the [PermissionManager] is used to request location permissions at runtime and handle the callbacks for permission granting or rejection.Additionally, you should pass the results of `Activity.onRequestPermissionResult()` to it. If the permissions are granted, call `mapView.getMapAsync(this)` to register the activity as a listener for onMapReady event.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/location/BasicLocationPulsingCircleActivity.kt:permission"
+
+```
+
+In the `onMapReady()` method, first set the style and then handle the user's location using the [LocationComponent].
+
+To configure the [LocationComponent], developers should use [LocationComponentOptions].
+
+In this demonstration, we create an instance of this class.
+
+In this method:
+
+- Use the annotation `@SuppressLint("MissingPermission")` to suppress warnings related to missing location access permissions.
+- In `setStyle(),` you can utilize other public and token-free styles like [demotiles] instead of the [predefined styles].
+- For the builder of [LocationComponentOptions], use `pulseEnabled(true)` to enable the pulse animation, which enhances awareness of the user's location.
+- Use method `buildLocationComponentActivationOptions()` to set [LocationComponentActivationOptions], then activate `locatinoComponent` with it.
+- To apply options, make sure you call `activateLocationComponent()` of `locationComponent`. You can also set `locationComponent`'s various properties like `isLocationComponentEnabled` , `cameraMode` , etc...
+- `CameraMode.TRACKING`[^1] means that when the user's location is updated, the camera will reposition accordingly.
+- `locationComponent!!.forceLocationUpdate(lastLocation)` updates the the user's last known location.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/location/BasicLocationPulsingCircleActivity.kt:onMapReady"
+```
+
+[LocationComponentActivationOptions] is used to hold the style, [LocationComponentOptions] and other locating behaviors.
+
+- It can also be used to configure how to obtain the current location, such as [LocationEngine] and intervals.
+- In this demonstration, it sets 750ms as the fastest interval for location updates, providing high accuracy location results (but with higher power consumption).
+- For more information, please visit the [documentation page][LocationComponentActivationOptions].
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/location/BasicLocationPulsingCircleActivity.kt:LocationComponentActivationOptions"
+```
+
+For further customization, you can also utilize the `foregroundTintColor()` and `pulseColor()` methods on the [LocationComponentOptions] builder:
+
+```kotlin
+val locationComponentOptions =
+ LocationComponentOptions.builder(this@BasicLocationPulsingCircleActivity)
+ .pulseEnabled(true)
+ .pulseColor(Color.RED) // Set color of pulse
+ .foregroundTintColor(Color.BLACK) // Set color of user location
+ .build()
+```
+
+Here is the final results with different color configurations. For the complete content of this demo, please refer to the source code of the [Test App].
+
+![result](https://github.com/maplibre/maplibre-native/assets/19887090/03dfc87b-111b-4dd0-b4a3-d89e30ed6b63)
+
+
+[^1]: A variety of [camera modes] determine how the camera will track the user location.
+ They provide the right context to your users at the correct time.
+
+[LocationComponent]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.location/-location-component/index.html
+[Android Developer Documentation]: https://developer.android.com/training/location/permissions
+[onMapReadyCallback]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.maps/-on-map-ready-callback/index.html
+[PermissionManager]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.location.permissions/-permissions-manager/index.html
+[LocationComponentOptions]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.location/-location-component-options/index.html
+[demotiles]: https://demotiles.maplibre.org/style.json
+[predefined styles]: https://github.com/maplibre/maplibre-native/tree/main/src/mbgl/util/tile_server_options.cpp
+[LocationComponentActivationOptions]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.location/-location-component-activation-options/index.html
+[LocationEngine]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.location.engine/-location-engine/index.html
+[Test APP]: https://github.com/maplibre/maplibre-native/tree/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/location/BasicLocationPulsingCircleActivity.kt
+[camera modes]: https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.location.modes/-camera-mode/index.html
diff --git a/platform/android/docs/snapshotter.md b/platform/android/docs/snapshotter.md
new file mode 100644
index 00000000000..89a17dbe217
--- /dev/null
+++ b/platform/android/docs/snapshotter.md
@@ -0,0 +1,163 @@
+# Using the Snapshotter
+
+This guide will help you walk through how to use [MapSnapshotter](https://maplibre.org/maplibre-native/android/api/-map-libre%20-native%20-android/org.maplibre.android.snapshotter/-map-snapshotter/index.html).
+
+## Map Snapshot with Local Style
+
+!!! note
+
+ You can find the full source code of this example in [`MapSnapshotterLocalStyleActivity.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterLocalStyleActivity.kt) of the MapLibreAndroidTestApp.
+
+To get started we will show how to use the map snapshotter with a local style.
+
+
+
+Add the [source code of the Demotiles style](https://github.com/maplibre/demotiles/blob/gh-pages/style.json) as `demotiles.json` to the `res/raw` directory of our app[^1]. First we will read this style:
+
+[^1]: See [App resources overview](https://developer.android.com/guide/topics/resources/providing-resources) for this and other ways you can provide resources to your app.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterLocalStyleActivity.kt:readStyleJson"
+```
+
+Next, we configure the MapSnapshotter, passing height and width, the style we just read and the camera position:
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterLocalStyleActivity.kt:createMapSnapshotter"
+```
+
+Lastly we use the `.start()` method to create the snapshot, and pass callbacks for when the snapshot is ready or for when an error occurs.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterLocalStyleActivity.kt:createSnapshot"
+```
+
+## Show a Grid of Snapshots
+
+!!! note
+
+ You can find the full source code of this example in [`MapSnapshotterActivity.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterActivity.kt) of the MapLibreAndroidTestApp.
+
+In this example, we demonstrate how to use the `MapSnapshotter` to create multiple map snapshots with different styles and camera positions, displaying them in a grid layout.
+
+
+
+First we create a [`GridLayout`](https://developer.android.com/reference/kotlin/android/widget/GridLayout) and a list of `MapSnapshotter` instances. We create a `Style.Builder` with a different style for each cell in the grid.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterActivity.kt:styleBuilder"
+```
+
+Next we create a `MapSnapshotter.Options` object to customize the settings of each snapshot(ter).
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterActivity.kt:mapSnapShotterOptions"
+```
+
+For some rows we randomize the visible region of the snapshot:
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterActivity.kt:setRegion"
+```
+
+For some columns we randomize the camera position:
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterActivity.kt:setCameraPosition"
+```
+
+In the last column of the first row we add two bitmaps. See the next example for more details.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterActivity.kt:addMarkerLayer"
+```
+
+## Map Snapshot with Bitmap Overlay
+
+!!! note
+
+ You can also find this code in [`MapSnapshotterBitMapOverlayActivity.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterBitMapOverlayActivity.kt) of the MapLibreAndroidTestApp.
+
+This example adds a bitmap on top of the snapshot. It also demonstrates how you can add a click listener to a snapshot.
+
+
+
+
+```kotlin title="MapSnapshotterBitMapOverlayActivity.kt"
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterBitMapOverlayActivity.kt"
+```
+
+## Map Snapshotter with Heatmap Layer
+
+!!! note
+
+ You can find the full source code of this example in [`MapSnapshotterHeatMapActivity.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterHeatMapActivity.kt) of the MapLibreAndroidTestApp.
+
+In this example, we demonstrate how to use the `MapSnapshotter` to create a snapshot of a map that includes a heatmap layer. The heatmap represents earthquake data loaded from a GeoJSON source.
+
+
+
+First, we create the `MapSnapshotterHeatMapActivity` class, which extends `AppCompatActivity` and implements `MapSnapshotter.SnapshotReadyCallback` to receive the snapshot once it's ready.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterHeatMapActivity.kt:class_declaration"
+```
+
+In the `onCreate` method, we set up the layout and initialize the `MapSnapshotter` once the layout is ready.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterHeatMapActivity.kt:onCreate"
+```
+
+Here, we wait for the layout to be laid out using an `OnGlobalLayoutListener` before initializing the `MapSnapshotter`. We create a `Style.Builder` with a base style (`TestStyles.AMERICANA`), add the earthquake data source, and add the heatmap layer above the "water" layer.
+
+The `heatmapLayer` property defines the `HeatmapLayer` used to visualize the earthquake data.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterHeatMapActivity.kt:heatmapLayer"
+```
+
+This code sets up the heatmap layer's properties, such as color ramp, weight, intensity, radius, and opacity, using expressions that interpolate based on data properties and zoom level.
+
+We also define the `earthquakeSource`, which loads data from a GeoJSON file containing earthquake information.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterHeatMapActivity.kt:earthquakeSource"
+```
+
+When the snapshot is ready, the `onSnapshotReady` callback is invoked, where we set the snapshot bitmap to an `ImageView` to display it.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterHeatMapActivity.kt:onSnapshotReady"
+```
+
+Finally, we ensure to cancel the snapshotter in the `onStop` method to free up resources.
+
+```kotlin
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/snapshot/MapSnapshotterHeatMapActivity.kt:onStop"
+```
+
+
+## Map Snapshotter with Expression
+
+!!! note
+
+ You can find the full source code of this example in [`MapSnapshotterWithinExpression.kt`](https://github.com/maplibre/maplibre-native/blob/main/platform/android/MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/turf/MapSnapshotterWithinExpression.kt) of the MapLibreAndroidTestApp.
+
+In this example the map on top is a live while the map on the bottom is a snapshot that is updated as you pan the map. We style of the snapshot is modified: using a [within](https://maplibre.org/maplibre-style-spec/expressions/#within) expression only POIs within a certain distance to a line is shown. A highlight for this area is added to the map as are various points.
+
+
+
+```kotlin title="MapSnapshotterWithinExpression.kt"
+--8<-- "MapLibreAndroidTestApp/src/main/java/org/maplibre/android/testapp/activity/turf/MapSnapshotterWithinExpression.kt"
+```
\ No newline at end of file
diff --git a/platform/android/mkdocs.yaml b/platform/android/mkdocs.yaml
new file mode 100644
index 00000000000..0370679c8d0
--- /dev/null
+++ b/platform/android/mkdocs.yaml
@@ -0,0 +1,74 @@
+site_name: MapLibre Android Examples
+site_url: https://www.maplibre.org/maplibre-native/android/examples
+repo_url: https://github.com/louwers/maplibre-native
+site_description: MapLibre Android Examples
+edit_uri: edit/main/platform/android/docs
+extra_css:
+ - assets/extra.css
+theme:
+ name: 'material'
+ favicon: https://maplibre.org/favicon.ico
+ logo: assets/logo.svg
+ features:
+ - content.code.copy
+ - search.suggest
+ - navigation.instant
+ - navigation.sections
+ - content.action.edit
+ palette:
+ - media: "(prefers-color-scheme)"
+ toggle:
+ icon: material/brightness-auto
+ name: Switch to light mode
+ - media: "(prefers-color-scheme: dark)"
+ scheme: slate
+ toggle:
+ icon: material/brightness-4
+ name: Switch to system preference
+ - media: "(prefers-color-scheme: light)"
+ scheme: default
+ toggle:
+ icon: material/brightness-7
+ name: Switch to dark mode
+markdown_extensions:
+ - pymdownx.highlight:
+ anchor_linenums: true
+ line_spans: __span
+ pygments_lang_class: true
+ - pymdownx.inlinehilite
+ - pymdownx.snippets:
+ dedent_subsections: true
+ - pymdownx.superfences
+ - pymdownx.escapeall:
+ hardbreak: True
+ nbsp: True
+ - admonition
+ - pymdownx.details
+ - footnotes
+ - attr_list
+ - md_in_html
+ - pymdownx.emoji:
+ emoji_index: !!python/name:material.extensions.emoji.twemoji
+ emoji_generator: !!python/name:material.extensions.emoji.to_svg
+extra:
+ social:
+ - icon: fontawesome/brands/mastodon
+ link: https://mastodon.social/@maplibre
+ - icon: fontawesome/brands/x-twitter
+ link: https://twitter.com/maplibre
+ - icon: fontawesome/brands/linkedin
+ link: https://www.linkedin.com/company/maplibre
+ - icon: fontawesome/brands/slack
+ link: https://osmus.slack.com/archives/C01G3D28DAB
+ - icon: fontawesome/brands/github
+ link: https://github.com/maplibre
+plugins:
+ - search
+ - social:
+ cards_layout_options:
+ background_color: '#295DAA'
+validation:
+ omitted_files: warn
+ absolute_links: warn
+ unrecognized_links: warn
+ anchors: warn