

leaflet で地図上に矢印を書きたいのですが  
矢印の先端部分を緯度経度に依存しない固定ピクセルの三角形を描画したいです

x1, x2, y1, y2 は緯度経度が入っていて

[code]

    L.polyline([x1, y1], [x2, y2]).addTo(map);
    
[/code]

でメインの直線を描画したあと

[code]

    L.polyline([x2, y2], [x2 - dx + dy, y2 - dy - dx], [x2 - dx - dy, y2 - dy + dx]).addTo(map);
    
[/code]

という感じで先端の三角形を書きたいので dx, dy を固定ピクセル分の長さを  
緯度経度に変換して渡したいです  
(測地系の偏差は無視して構わないです）

コメントで教えていただいた layerPointToLatLng を使うと  
ピクセル指定で図形描画はできたのですが  
描画したズームでの座標で固定してしまうと  
地図を拡大縮小すると潰れたり大きくなりすぎたりしてしまいます

CircleMarker のようにズームによって再描画した時固定のピクセルで描画するには  
どうすればいいんでしょうか

自前の arrow_line みたいなクラスを line を継承して作って  
再描画メソッドをオーバーライドして zoomlevel から座標を再計算して描画する  
というようなことをするしかないのでしょうか


CC BY-SA 4.0
2020-04-03T03:48:03.503
65321
2022-05-16T21:00:20.093
2020-04-03T06:38:39.673
question
leaflet
leaflet で zoom を変更したときにも固定ピクセルで図形を描画したい


[CircleMarker](https://leafletjs.com/reference-1.6.0.html#circlemarker)のように描画したい場合は、単純にアイコン付き[Marker](https://leafletjs.com/reference-1.6.0.html#marker)を使用する方法もご検討ください。  
CircleMarkerと同様にマウスオーバーでマウスカーソルが変わりますが、けっこう良い感じに描画されます。  
背景を透過した三角形素材：[![背景を透過した三角形](https://i.stack.imgur.com/kpYra.png)](https://i.stack.imgur.com/kpYra.png)  
ズーム前後の表示例：  
[![ズーム前後の表示例](https://i.stack.imgur.com/Kusqt.jpg)](https://i.stack.imgur.com/Kusqt.jpg)

[code]

    <!DOCTYPE html>
    <html lang="ja">
    <head>
      <!-- このコードはオフライン作業では動きません -->
      <title>Leaflet</title>
      <meta charset="UTF-8">
      <meta name="viewport" content="width=device-width, initial-scale=1">
      <link rel="stylesheet" href="https://unpkg.com/leaflet@1.6.0/dist/leaflet.css" />
      <script src="https://unpkg.com/leaflet@1.6.0/dist/leaflet.js"></script>
    <style>
      body { margin:0; padding:0; }
      #map { position:absolute; top:0; bottom:0; width:100%; }
    </style>
    </head>
    <body>
    <div id='map'></div>
    </body>
    <script>
    
    var map = L.map("map");
    L.tileLayer("http://{s}.tile.osm.org/{z}/{x}/{y}.png").addTo(map);
    map.setView([35.68, 139.77], 12);
    // 無意味なサンプル直線
    var my_line = L.polyline([[35.68, 139.77], [34.7, 135.5]], {color: 'red'}).addTo(map);
    // 三角形のアイコン iconSizeはpngのサイズ、 iconAnchorで三角形の先端を直線の末尾に合わせる
    var my_icon = L.icon({iconUrl: 'triangle.png', iconSize: [36, 32], iconAnchor: [16, 0] });
    // 三角形を描画するだけのマーカー
    var my_marker = L.marker([35.68, 139.77], {icon: my_icon}).addTo(map);
    
    </script>
    </html>
    
[/code]

なお`zoomlevel`から座標を再計算して描画するならば、オーバーライドよりも[zoomend](https://leafletjs.com/reference-1.6.0.html#map-
zoomend)イベントを使って再描画する方が手軽かと思います。


CC BY-SA 4.0
2020-04-04T08:04:28.213
65348
2020-04-04T08:04:28.213
9820
65321
answer