Googleマップ上の動的テーブル

はじめに


マップバインドで大きなデータセットを表示する必要がありましたか? 職場では、緯度と経度でグループ化された注文を表示する必要がありました。 また、静的なテーブルだけでなく、マップ近似ごとに詳細が異なる動的なテーブルもあります。


残念ながら(または幸いなことに)、既成のソリューションは見つかりませんでした。 Googleマップでは、マーカーと図形を地図に重ねることができますが、これらの方法では情報が少なすぎます。 Yandexカードを使用した場合、それは良くないことが判明しました。 ただし、GoogleマップにはHTMLコンテンツを使用したカスタムオーバーレイメカニズムがあります。 この作業をマップとオーバーレイでカプセル化するために、GMapsTable JavaScriptライブラリを作成しました。 おそらく誰かがそれを面白く、または役に立つと思うでしょう。 作業例。


screen0


screen1


コンベンション

混乱を避けるために、ズームパラメータはマップ近似と呼ばれ、スケールはスケールです。 1つ目はGoogle Maps APIに関連し、2つ目は説明したライブラリに関連しています。


全体的なタスク


では、何がありますか? 何らかの種類のデータソース(たとえば、JSON形式でデータを処理および送信するデータベースサーバー)と、データを要求してGoogleマップに表示するJavaScript Webページ。


データは累積的な性質のものです(私の場合、各エリアは、注文数、顧客数、平均金額に関連付けることができます)。 したがって、データは、さまざまな近似のさまざまな粒度で表示できます。


GMapsTableのHTMLページのメインコンテンツ:


.. <head>: <script src="https://maps.googleapis.com/maps/api/js?key=YOUR_KEY"></script> <script src="http://www.aivanf.com/static/gmt/gmapstable.js"></script> .. <body>: <div id="map"></div> 

GMapsTableを使用すると、GoogleMaps APIとの相互作用を無視できます。 適切なデータオブジェクトのみを提供する必要があります。 JavaScript'yにジャンプする時間です! GMapsTableを使用するには、マップdivのDataContainerオブジェクトを取得するだけです。


 // : ID div' //    GoogleMaps, //    var container = new DataContainer("map", { zoom: 9, center: {lat: 55.7558, lng: 37.6173}, mapTypeId: 'roadmap' }); 

そして、いくつかの関数を渡す必要があります。


 container.dataLoader = function (scale, borders) { ...  container.processData(some_data); } container.scaler = function (zoom) { ... return - ; } 

しかし、関数の内部には正確に何を書くべきですか?..まず、GMapsTableの仕組みを理解しましょう。


DataContainerのデータ


DataContainerはデータの表示を処理し、いつデータを更新すべきかを処理します。 最初に、「カメラ」の近似値と境界が変わると、保存されたデータを使用しようとし、データがない場合はdataLoader関数を呼び出します。 データを含むオブジェクトを生成し、それをDataContainer.processData関数に渡す必要があります。 オブジェクトの構造は次のようになります。


 data: { minLat: float, difLat: float, minLon: float, difLon: float, scale: int, table: [ [value, value, ...], [value, value, ...], ... ], tocache: boolean } 

テーブルセルに独自の書式設定関数を指定する場合、 valueは数値、文字列、または任意のオブジェクトにできます。 スケール( sale )は、緯度と経度の単位を分割する部分の数を示す整数です。 tocacheパラメーターは、現在のスケールのデータを保存し、要求しないようにするかどうかを指定します。


データオブジェクトの例
 data: { minLat: 55.0, difLat: 2.0, minLon: 37.0, difLon: 1.0, scale: 2, table: [ [1, 3, 0, 1], [0, 1, 2, 0] ], tocache: true } 

ここでは、データは55.0、37.0から57.0、38.0までの領域をカバーし、緯度と経度の各単位を2つの部分に分割しています(緯度と経度の1つのセルが4つの部分に分割されていることがわかります)。 また、ここでは、特定のスケールでこれが完全なデータであり、将来の参照のために保存する必要があることも示されています。


ズームを縮尺に変換


ズームは、Google Maps APIのパラメーターであり、1(世界地図)〜22(通り)の整数です。 各近似単位のデータを要求して保存するのは不便で非実用的です。したがって、GMapsTableはそれらをスケール(緯度と経度の単位を分割する部分の数を示す数値)に変換します。


データ保存


ズーム時にすぐに表示するために、GMapsTableは一部(またはすべて)の縮尺のデータセットを保存します。 たとえば、ロシアのほぼすべてからの座標を持つデータベースがありました-スケール10(500 KB、デスクトップブラウザーでの保存と処理が非常に簡単です)で約42,000セル、スケール200(数MB、大幅なフリーズを引き起こす)で1,700万セル。 したがって、サーバーはすべてのデータのセルの数を推定し、あまり多くない場合はデータベース全体からデータを送信します。 次のアルゴリズムが判明します。


GMapsTableテーブル更新アルゴリズム


境界線( bounds )は、フィールドminlat, maxlat, minlon, maxlon持つJavaScriptオブジェクトですminlat, maxlat, minlon, maxlonの現在の境界線と十分なマージンがあります。


dataLoader実装ではdataLoader異なるスケールに異なる粒度を使用する必要がない場合、またはデータがそのような大きな領域をカバーしていない場合、引数を安全に無視できます。 緯度と経度とscaleでデータとその境界を渡すだけで、緯度経度の単位をどれだけ分割できます。 しかし、図を完成させるために、 dataLoader関数(またはそれが参照するサーバー)のこの動作をお勧めします。


GMapsTableのデータオブジェクト生成アルゴリズム


すべてのパラメーターのリスト


DataContainerには次のパラメーターを指定できます。


1) scaler(zoom) -GoogleMapsからの近似値をGMapsTableのスケールに変換します。 両方とも整数です。


2) dataLoader(scale, borders) -新しいデータが必要なときに呼び出されます。 データオブジェクトをDataContainer.processData(data)渡す必要があります。


borders引数は、フィールドminlat, maxlat, minlon, maxlon持つJavaScriptオブジェクトですminlat, maxlat, minlon, maxlonの現在の境界と予備の十分なマージンがあります。


3) tableBeforeInit(map, table, data) -テーブルがセルで埋められる前に呼び出されます。 map引数はGoogle Mapsオブジェクト、 tableは作成されたテーブルのHTML要素、 dataは現在の縮尺に対して指定したdataオブジェクトです。 ここで、テーブル、現在のデータまたは現在のマップパラメーターを使用する変数を構成できます。


4) cellFormatter(td, val) -セルを埋めるために呼び出されます。 tdはHTML要素、テーブルセルです。 valはデータオブジェクトからのデータです。 ここでは、パラメータに従って、いくつかの値の出力または色の塗りつぶしを簡単に構成できます。


5) boundsChangedListener(zoom)boundsChangedListener(zoom)マップの境界線が変更されたときに呼び出されます。


6) minZoomLevelmaxZoomLevelマップの最小および最大近似の変数。 1(世界地図)から22(通り)までの整数。


DataContainerを正常に操作するには、最初の2つの機能のみが必要です。


例とソース


完全でコメントの多い使用例: HTMLページJSコード
また、 GitHubにGMapsTableもあります



Source: https://habr.com/ru/post/J330920/


All Articles