Connect Data to the Map - Kotlin SDK
This example shows how you can add earthquake data from GeoJSON onto the map, and use circle layer and markers to visualize it. User can tap each marker to get the title of the earthquake.
In addition to markers and circle layer, you can use symbol, line and fill layers to visualize your data.
import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.runtime.Composable
import androidx.compose.runtime.DisposableEffect
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Modifier
import com.maptiler.maptilersdk.MTConfig
import com.maptiler.maptilersdk.annotations.MTTextPopup
import com.maptiler.maptilersdk.annotations.MTMarker
import com.maptiler.maptilersdk.map.LngLat
import com.maptiler.maptilersdk.map.MTMapOptions
import com.maptiler.maptilersdk.map.MTMapView
import com.maptiler.maptilersdk.map.MTMapViewController
import com.maptiler.maptilersdk.map.MTMapViewDelegate
import com.maptiler.maptilersdk.map.style.MTMapReferenceStyle
import com.maptiler.maptilersdk.map.style.MTMapStyleVariant
import com.maptiler.maptilersdk.map.style.MTStyle
import com.maptiler.maptilersdk.map.types.MTData
import com.maptiler.maptilersdk.map.style.source.MTGeoJSONSource
import com.maptiler.maptilersdk.map.style.layer.circle.MTCircleLayer
import com.maptiler.maptilersdk.map.style.layer.circle.colorConst
import com.maptiler.maptilersdk.map.style.layer.circle.radiusConst
import com.maptiler.maptilersdk.events.MTEvent
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import org.json.JSONArray
import org.json.JSONObject
import java.net.URL
class EarthquakesPopupsComposeActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
// Replace with your MapTiler API key
MTConfig.apiKey = "MY_API_KEY"
setContent {
EarthquakesPopupsComposeMap()
}
}
}
@Composable
fun EarthquakesPopupsComposeMap(context: Context) {
val controller = remember { MTMapViewController(context) }
val scope = rememberCoroutineScope()
LaunchedEffect(controller) {
controller.delegate = object : MTMapViewDelegate {
override fun onMapViewInitialized() {
scope.launch { loadEarthquakesAndStyle(controller) }
controller.setZoom(1.8)
}
override fun onEventTriggered(event: MTEvent, data: MTData?) { /* no-op */ }
}
}
DisposableEffect(controller) { onDispose { controller.delegate = null } }
MTMapView(
referenceStyle = MTMapReferenceStyle.SATELLITE,
options = MTMapOptions(),
controller = controller,
modifier = Modifier.fillMaxSize(),
)
}
private suspend fun loadEarthquakesAndStyle(controller: MTMapViewController) {
val style = controller.style ?: return
val url = URL("https://docs.maptiler.com/sdk-js/assets/significant-earthquakes-2015.geojson")
val jsonString = withContext(Dispatchers.IO) { url.readText() }
runCatching {
val source = MTGeoJSONSource.fromJsonString(
identifier = "significant-earthquakes-2015",
json = jsonString,
)
style.addSource(source)
}
addEarthquakesCircleLayer(style)
val features = JSONObject(jsonString).optJSONArray("features") ?: JSONArray()
for (i in 0 until features.length()) {
val feature = features.optJSONObject(i) ?: continue
val properties = feature.optJSONObject("properties") ?: continue
val title = properties.optString("title", null) ?: continue
val geometry = feature.optJSONObject("geometry") ?: continue
if (geometry.optString("type") != "Point") continue
val coords = geometry.optJSONArray("coordinates") ?: continue
if (coords.length() < 2) continue
val lon = coords.optDouble(0)
val lat = coords.optDouble(1)
val ll = LngLat(lon, lat)
val popup = MTTextPopup(ll, title, offset = 10.0)
val marker = com.maptiler.maptilersdk.annotations.MTMarker(ll).apply { this.popup = popup }
style.addMarker(marker)
}
}
private fun addEarthquakesCircleLayer(style: MTStyle) {
val layer = MTCircleLayer(
identifier = "significant-earthquakes-circles",
sourceIdentifier = "significant-earthquakes-2015",
).apply {
colorConst(0xFF5722) // deep orange
radiusConst(6.0)
}
style.addLayer(layer)
}
On this page