diff --git a/src/main/java/com/mapconductor/tomtom/TomTomMapViewController.kt b/src/main/java/com/mapconductor/tomtom/TomTomMapViewController.kt index 50be728..2158ce9 100644 --- a/src/main/java/com/mapconductor/tomtom/TomTomMapViewController.kt +++ b/src/main/java/com/mapconductor/tomtom/TomTomMapViewController.kt @@ -284,6 +284,8 @@ class TomTomMapViewController internal constructor( } private suspend fun restackPolylines() { + // Drawn as tiles: the tile layer has its own order, and clearing would tile them all again. + if (polylineController.tiler?.tiledStates()?.isNotEmpty() == true) return val states = polylineController.polylineManager.allEntities().map { it.state } if (states.isEmpty()) return polylineController.clear() diff --git a/src/main/java/com/mapconductor/tomtom/TomTomMapViewControllerRaster.kt b/src/main/java/com/mapconductor/tomtom/TomTomMapViewControllerRaster.kt index 027e3ef..e586846 100644 --- a/src/main/java/com/mapconductor/tomtom/TomTomMapViewControllerRaster.kt +++ b/src/main/java/com/mapconductor/tomtom/TomTomMapViewControllerRaster.kt @@ -2,6 +2,8 @@ package com.mapconductor.tomtom import com.mapconductor.core.polygon.POLYGON_TILE_LAYER_ID import com.mapconductor.core.polygon.PolygonTiler +import com.mapconductor.core.polyline.POLYLINE_TILE_LAYER_ID +import com.mapconductor.core.polyline.PolylineTiler import com.mapconductor.core.raster.RasterLayerSource import com.mapconductor.core.raster.RasterLayerState import com.mapconductor.tomtom.marker.MarkerTileRasterLayerCallback @@ -60,6 +62,17 @@ fun TomTomMapViewController.setupMarkerTileRaster( } } } + // Many polylines too, the same way (over the polygon tiles, under the SDK's overlays). + polylineController.tiler = + PolylineTiler().apply { + onTemplate = { template, tileSize -> + if (template != null) { + upsertRasterLayer(POLYLINE_TILE_LAYER_ID, template, 1.0, tileSize, null, null) + } else { + removeRasterLayer(POLYLINE_TILE_LAYER_ID) + } + } + } } internal suspend fun TomTomMapViewController.applyPublicRasterLayer(state: RasterLayerState) { @@ -110,13 +123,16 @@ internal suspend fun TomTomMapViewController.applyComposedStyle() { } composedStyleToggle = composedStyleToggle xor 1 val outFile = File(cacheDir, "tomtom_composed_style_$composedStyleToggle.json") - // アプリのラスターはラスターの帯(SDK のオーバーレイの下)、マーカーのタイルはマーカーの帯(最前面)。 - // ポリゴンのタイルはアプリのラスターのすぐ上(SDK のオーバーレイの下)。ポリゴンの帯は - // GroundImage の上だが、TomTom の GroundImage はネイティブの Polygon(SDK のオーバーレイ)で、 - // スタイルの層をその間へは入れられない。サークル・ポリライン・マーカーの下は守れる。 + // アプリのラスターはラスターの帯(ベースマップのラベルの下)、マーカーのタイルはマーカーの帯(最前面)。 + // ポリゴンのタイルはアプリのラスターのすぐ上(ラベルの下)。ネイティブのサークル・ポリゴン + // (SDK のオーバーレイ)はその上に来る。ポリラインのタイルはベースマップの全レイヤー(道路・ラベル)の + // 上: TomTom のスタイルは最初のラベルの後ろにも道路の line が続くので、ラベルの前では道路のタイルが + // 地図の道路に覆われて見えなかった。ネイティブのサークルより上・マーカー(とそのタイル)より下になる + // (実機で確認。ポリゴンのタイルまで上へ上げるとサークルを覆ってしまう)。 val (markerTiles, others) = composedRasterLayers.values.partition { it.id == TomTomMapViewController.MARKER_RASTER_ID } - val (polygonTiles, appRasters) = others.partition { it.id == POLYGON_TILE_LAYER_ID } + val (polylineTiles, rest) = others.partition { it.id == POLYLINE_TILE_LAYER_ID } + val (polygonTiles, appRasters) = rest.partition { it.id == POLYGON_TILE_LAYER_ID } val uri = TomTomStyleComposer.composeStackedRasterStyle( apiKey = apiKey, @@ -125,6 +141,7 @@ internal suspend fun TomTomMapViewController.applyComposedStyle() { aboveOverlays = markerTiles, outFile = outFile, withoutBasemap = withoutBasemap, + polylineTiles = polylineTiles, ) ?: return if (destroyed) return withContext(Dispatchers.Main) { diff --git a/src/main/java/com/mapconductor/tomtom/raster/TomTomStyleComposer.kt b/src/main/java/com/mapconductor/tomtom/raster/TomTomStyleComposer.kt index a4fd5e4..b5b265f 100644 --- a/src/main/java/com/mapconductor/tomtom/raster/TomTomStyleComposer.kt +++ b/src/main/java/com/mapconductor/tomtom/raster/TomTomStyleComposer.kt @@ -101,6 +101,9 @@ object TomTomStyleComposer { * (ラスター < GroundImage < ポリゴン < サークル < ポリライン < マーカー)でいちばん下の帯なので、 * SDK のオーバーレイ用レイヤー(polygon-shape など)とベースマップのラベルより**下**へ、 * 渡された順(下→上)に入れる。 + * - [polylineTiles]: SDK 自身のポリラインのタイル(下→上)。スタイルの全レイヤー(ベースマップの + * 道路・ラベルも含む)の上、マーカーのタイルの下へ。TomTom のスタイルは最初の symbol の後ろにも + * 道路の line レイヤーが続くので、ラベルの前に入れると道路のタイルが地図の道路に覆われて見えなかった。 * - [aboveOverlays]: マーカーのタイル。マーカーの帯なのでスタイルの末尾(最前面)へ。 * * 以前はどちらも末尾に積んでいたため、アプリのラスターがポリゴン・ポリライン・ @@ -113,6 +116,7 @@ object TomTomStyleComposer { aboveOverlays: List, outFile: File, withoutBasemap: Boolean, + polylineTiles: List = emptyList(), ): Uri? = withContext(Dispatchers.IO) { // The SDK will not take a style that has none of its own layers @@ -201,9 +205,16 @@ object TomTomStyleComposer { insertLayerAt(styleLayers, insertBelow, rasterLayer("mc-raster-layer-$index", sourceId, spec.opacity)) insertBelow++ } + // ポリラインのタイル: ベースマップの全レイヤーの上へ順に。 + polylineTiles.forEachIndexed { i, spec -> + val index = belowOverlays.size + i + val sourceId = "mc-raster-src-$index" + sources.put(sourceId, rasterSource(spec.tilesUrl, spec.tileSize, spec.minZoom, spec.maxZoom)) + styleLayers.put(rasterLayer("mc-raster-layer-$index", sourceId, spec.opacity)) + } // マーカーのタイル: 最前面(末尾)へ順に重ねる。 aboveOverlays.forEachIndexed { i, spec -> - val index = belowOverlays.size + i + val index = belowOverlays.size + polylineTiles.size + i val sourceId = "mc-raster-src-$index" sources.put(sourceId, rasterSource(spec.tilesUrl, spec.tileSize, spec.minZoom, spec.maxZoom)) styleLayers.put(rasterLayer("mc-raster-layer-$index", sourceId, spec.opacity)) @@ -218,7 +229,7 @@ object TomTomStyleComposer { Log.i( TAG, "Composed style written (${outFile.length()} bytes, ${styleLayers.length()} layers, " + - "${belowOverlays.size + aboveOverlays.size} raster)", + "${belowOverlays.size + polylineTiles.size + aboveOverlays.size} raster)", ) Uri.fromFile(outFile) }