What You'll Learn
Google Maps + Compose応用(Marker Clustering、Custom Markers、ジオコーディング、Route Drawing、ヒートマップ)を解説します。
Setup
dependencies {
implementation("com.google.maps.android:maps-compose:6.2.1")
implementation("com.google.maps.android:maps-compose-utils:6.2.1")
implementation("com.google.android.gms:play-services-maps:19.0.0")
}
Custom Markers
@Composable
fun CustomMarkerMap(spots: List<Spot>) {
val cameraPositionState = rememberCameraPositionState {
position = CameraPosition.fromLatLngZoom(
LatLng(35.6812, 139.7671), 12f // 東京
)
}
GoogleMap(
modifier = Modifier.fillMaxSize(),
cameraPositionState = cameraPositionState
) {
spots.forEach { spot ->
MarkerComposable(
keys = arrayOf(spot.id),
state = MarkerState(position = LatLng(spot.lat, spot.lng))
) {
// ComposeでCustom MarkersUI
Card(
colors = CardDefaults.cardColors(
containerColor = MaterialTheme.colorScheme.primaryContainer
),
shape = RoundedCornerShape(8.dp)
) {
Text(
spot.name,
Modifier.padding(horizontal = 8.dp, vertical = 4.dp),
style = MaterialTheme.typography.labelSmall
)
}
}
}
}
}
Marker Clustering
@Composable
fun ClusteredMap(items: List<SpotClusterItem>) {
val cameraPositionState = rememberCameraPositionState()
GoogleMap(
modifier = Modifier.fillMaxSize(),
cameraPositionState = cameraPositionState
) {
Clustering(
items = items,
onClusterClick = { cluster ->
// クラスタクリック: ズームイン
cameraPositionState.move(
CameraUpdateFactory.newLatLngZoom(cluster.position, 15f)
)
true
},
onClusterItemClick = { item ->
// 個別マーカークリック
false
},
clusterContent = { cluster ->
Box(
Modifier.size(40.dp).background(
MaterialTheme.colorScheme.primary, CircleShape
),
contentAlignment = Alignment.Center
) {
Text("${cluster.size}", color = Color.White, fontWeight = FontWeight.Bold)
}
}
)
}
}
data class SpotClusterItem(
val spot: Spot,
val itemPosition: LatLng = LatLng(spot.lat, spot.lng),
val itemTitle: String = spot.name
) : ClusterItem {
override fun getPosition() = itemPosition
override fun getTitle() = itemTitle
override fun getSnippet() = spot.description
override fun getZIndex() = 0f
}
Polyline (Route Drawing)
@Composable
fun RouteMap(routePoints: List<LatLng>) {
val cameraPositionState = rememberCameraPositionState()
GoogleMap(
modifier = Modifier.fillMaxSize(),
cameraPositionState = cameraPositionState
) {
Polyline(
points = routePoints,
color = MaterialTheme.colorScheme.primary,
width = 8f,
pattern = listOf(Dot(), Gap(10f))
)
if (routePoints.isNotEmpty()) {
Marker(state = MarkerState(routePoints.first()), title = "出発")
Marker(state = MarkerState(routePoints.last()), title = "到着")
}
}
}
Summary
| 機能 | API |
|---|---|
| Custom Markers | MarkerComposable |
| クラスタリング | Clustering |
| Route Drawing | Polyline |
| 円/多角形 |
Circle / Polygon
|
| カメラ操作 | CameraPositionState |
-
MarkerComposableでComposeウィジェットをマーカーに -
Clusteringで大量マーカーをグループ化 -
Polylineでルートや経路を描画 -
maps-composeでGoogle MapsをCompose完全統合
8種類のAndroidAppTemplates(MapsIntegration Support)を公開しています。
Template List → Gumroad
Related Articles:
Ready-Made Android App Templates
8 production-ready Android app templates with Jetpack Compose, MVVM, Hilt, and Material 3.
Browse templates → Gumroad
Top comments (0)