Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions api/android-for-here.api
Original file line number Diff line number Diff line change
Expand Up @@ -192,6 +192,8 @@ public final class com.mapconductor.here.HereOverlayStacking {
public final com.here.sdk.mapview.MapLayerPriority rasterPriority();
public final com.here.sdk.mapview.MapLayerPriority groundImagePriority();
public final com.here.sdk.mapview.MapLayerPriority polygonTilePriority();
public final com.here.sdk.mapview.MapLayerPriority polygonTilePriority(java.lang.String);
public final com.here.sdk.mapview.MapLayerPriority polylineTilePriority(java.lang.String);
}
public final class com.mapconductor.here.HereTypeAliasKt {
}
Expand Down
15 changes: 15 additions & 0 deletions src/main/java/com/mapconductor/here/HereMapViewController.kt
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,10 @@ import com.mapconductor.core.marker.StrategyMarkerController
import com.mapconductor.core.marker.dispatchGeoMarkerClick
import com.mapconductor.core.polygon.OnPolygonEventHandler
import com.mapconductor.core.polyline.OnPolylineEventHandler
import com.mapconductor.core.polyline.POLYLINE_TILE_LAYER_ID
import com.mapconductor.core.polyline.PolylineState
import com.mapconductor.core.polyline.PolylineTiler
import com.mapconductor.core.polyline.polylineTileRasterLayerState
import com.mapconductor.here.circle.HereCircleController
import com.mapconductor.here.groundimage.HereGroundImageController
import com.mapconductor.here.marker.HereMarkerController
Expand Down Expand Up @@ -185,6 +188,18 @@ class HereMapViewController(
}
}
}

// Many polylines too: the same raster layer path, in the polyline band.
polylineController.tiler =
PolylineTiler().apply {
onTemplate = { template, tileSize ->
if (template != null) {
rasterLayerController.upsert(polylineTileRasterLayerState(template, tileSize))
} else {
rasterLayerController.removeById(POLYLINE_TILE_LAYER_ID)
}
}
}
}

override fun moveCamera(position: MapCameraPosition) = handleMoveCamera(position)
Expand Down
22 changes: 21 additions & 1 deletion src/main/java/com/mapconductor/here/HereOverlayStacking.kt
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,27 @@ internal object HereOverlayStacking {
* ポリゴンのタイル(SDK が描くラスター): ポリゴンの帯の一番下。GroundImage のアンカー
* "traffic_on_route" の直後(GroundImage より上、map item より下)。
*/
fun polygonTilePriority(): MapLayerPriority = MapLayerPriorityBuilder().renderedAfterLayer(GROUND_IMAGE_ANCHOR).build()
fun polygonTilePriority(): MapLayerPriority = polygonTilePriority(beforeLayer = null)

/** [polygonTilePriority]; when the polyline tiles are already on the map, just below them ([beforeLayer]). */
fun polygonTilePriority(beforeLayer: String?): MapLayerPriority =
if (beforeLayer != null) {
MapLayerPriorityBuilder().renderedBeforeLayer(beforeLayer).build()
} else {
MapLayerPriorityBuilder().renderedAfterLayer(GROUND_IMAGE_ANCHOR).build()
}

/**
* ポリラインのタイル(SDK が描くラスター): ポリゴンのタイルの上([afterLayer]、無ければ
* GroundImage のアンカーの直後)、map item の下。
*
* HERE の map item(ポリゴン・サークル・ポリライン)は 1 枚の層にまとめて描かれ、
* MapLayer をサークルとポリラインの間に挟めない。map item の下に置くので、ネイティブの
* ポリゴン・サークルもこのタイルの上に来る(帯の決まりからの、HERE だけの差)。
* マーカーとマーカーのタイルより下、ポリゴンのタイルより上は守る。
*/
fun polylineTilePriority(afterLayer: String?): MapLayerPriority =
MapLayerPriorityBuilder().renderedAfterLayer(afterLayer ?: GROUND_IMAGE_ANCHOR).build()

private const val RASTER_ANCHOR = "route"
private const val GROUND_IMAGE_ANCHOR = "traffic_on_route"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import com.here.sdk.mapview.datasource.TileUrlProviderCallback
import com.here.sdk.mapview.datasource.TileUrlProviderFactory
import com.here.sdk.mapview.datasource.TilingScheme
import com.mapconductor.core.polygon.POLYGON_TILE_LAYER_ID
import com.mapconductor.core.polyline.POLYLINE_TILE_LAYER_ID
import com.mapconductor.core.raster.RasterLayerEntityInterface
import com.mapconductor.core.raster.RasterLayerOverlayRendererInterface
import com.mapconductor.core.raster.RasterLayerSource
Expand Down Expand Up @@ -140,6 +141,7 @@ class HereRasterLayerOverlayRenderer(
.forMap(holder.mapView.hereMap)
.build()
layer.setEnabled(state.visible)
if (isShapeTileLayer(state.id)) shapeTileLayers.add(state.id)
HereRasterLayerHandle(
dataSource = dataSource,
layer = layer,
Expand All @@ -155,20 +157,35 @@ class HereRasterLayerOverlayRenderer(
}
}

/** The SDK's shape tile layers on the map now (their ids), so each can be placed against the other. */
private val shapeTileLayers = java.util.Collections.synchronizedSet(HashSet<String>())

/**
* アプリのラスターはラスターの帯(GroundImage・map item の下)。マーカーのタイルは
* マーカーの帯なので、ポリゴン等の map item より上(最後に描く)。ポリゴンのタイルは
* ポリゴンの帯の一番下(GroundImage の上、map item の下)。
* ポリゴンの帯の一番下(GroundImage の上、map item の下)。ポリラインのタイルはその上
* ([HereOverlayStacking.polylineTilePriority])。どちらも版が変わるたびに作り直すので、
* もう片方があればそれを基準に置き、作った順に左右されないようにする。
*/
private fun priorityFor(state: RasterLayerState): MapLayerPriority =
if (state.id.startsWith("marker-tile-")) {
MapLayerPriorityBuilder().renderedLast().build()
} else if (state.id == POLYGON_TILE_LAYER_ID) {
HereOverlayStacking.polygonTilePriority()
HereOverlayStacking.polygonTilePriority(
beforeLayer = layerNameOf(POLYLINE_TILE_LAYER_ID).takeIf { POLYLINE_TILE_LAYER_ID in shapeTileLayers },
)
} else if (state.id == POLYLINE_TILE_LAYER_ID) {
HereOverlayStacking.polylineTilePriority(
afterLayer = layerNameOf(POLYGON_TILE_LAYER_ID).takeIf { POLYGON_TILE_LAYER_ID in shapeTileLayers },
)
} else {
HereOverlayStacking.rasterPriority()
}

private fun layerNameOf(id: String) = "raster-layer-$id"

private fun isShapeTileLayer(id: String) = id == POLYGON_TILE_LAYER_ID || id == POLYLINE_TILE_LAYER_ID

private fun updateLayer(
handle: HereRasterLayerHandle,
state: RasterLayerState,
Expand All @@ -178,6 +195,7 @@ class HereRasterLayerOverlayRenderer(

private fun removeLayer(entity: RasterLayerEntityInterface<HereRasterLayerHandle>) {
val handle = entity.layer
if (isShapeTileLayer(entity.state.id)) shapeTileLayers.remove(entity.state.id)
handle.routeId?.let { tileServer.unregister(it) }
handle.layer.destroy()
handle.dataSource.destroy()
Expand Down
Loading