見出し画像

WebixライブラリとGoogleMap連携(マーカ表示、軌跡表示他)No.051

以前に、スマホ用Webアプリで、GPS情報の収集やカメラ撮影した画像を保存して作業日報を作成する記事を何回かに分割して公開していますが、今回は、GoogleMap機能をさらに活用するWebアプリを作るための基盤情報の紹介です。まだ、アプリとしては実装していませんが、画面動作を確認するためのプロト作成をしましたので、紹介します。
Webixライブラリには、GoogleMapと連携できるコンポーネントが実装されています。


作業日報でもスマホで取得したGPS情報をマップ上に表示するためにGoogleMapというコンポーネントを使っています。
GoogleMapをJavascriptから制御するには、事前にAPIキーの取得が必要です。この記事では詳しい説明は省略しますが、Web上に多くの記事がありますので、その記事を参考にしてAPIキーの取得と環境設定が必要です。
今回の記事では、スマホからGPS情報を周期的または、手動操作タイミングで取得し、サーバ上に格納してから、ビューワを起動したときに、そのGPS情報をマップ上に表示するためのGUI側の基本動作事例です。
今回のソースは、Wbixライブラリが提供しているsnipeteditorで動作させています。

https://snippet.webix.com/basic

以下のURLにアクセスすれば、パソコン上で動作確認できます。

画面には、ソースコードとそのソースコードが実行されたときの画面が表示されています。

このソースは、上記URL上のサーバからの操作でしかGoogleMap動作しません。(APIKEYが制限されています)

var google_map_api_key = "AIzaSyAi0oVNVO-e603aUY8SILdD4v9bVBkmiTg";
部分を変更すれば、別サーバからでも動作します。
(上記ソースは、Webサーバで動作するためのソースは省略されていますので、そのままでは動作しませんが)

WebixライブラリでGoogleMapを使うには、google-mapというコンポーネントを使います。
以下の記述で、使用できます。(初期値は、地図表示のみで、マーカや軌跡は未表示です)
地図の中心の緯度・経度の指定と、地図のZoomレンジを指定します。
このデモでは、新横浜駅周辺を16サイズで表示するように指定しています。

    {
      key:google_map_api_key ,
      view:"google-map",
      id:"map",
      zoom:map_zoom_size,
      center:map_center_info,
      data:[]
    }

マーカは、1つのマップに複数描画できます。addメソッドで、緯度・経度とマウスフォーカス時のメモ情報などを指定します。
変数名などは、適当ですが、緯度・経度の配列情報に従って、マップ上にマーカをプロットします。

var marker_array =[
{ id:1, lat:35.507853, lng:139.617064, title:"スタート" },
{ id:3, lat:35.509817987733584,lng:139.61617335684315, title:"途中で休憩",info:"memo" },
{ id:7, lat:35.50953845551983, lng:139.61095898793627, title:"撮影2",info:"photo"  },
{ id:9, lat:35.510796030972664,lng:139.6086735567171,title:"もうすぐ到着",info:"memo" },
{ id:10, lat:35.51082220178137, lng:139.60804051507876, title:"終了",info:"photo" }
];

              //マーカをマップに描画
              marker_array.forEach(function( item ) {
                  $$("map").add(item );
	          });


軌跡情報は、以下のように指定して線で結ぶことができます。

 var polyline_array = [
	{ id:1, lat:35.507853, lng:139.617064},
	{ id:2, lat:35.508281, lng:139.616763},
	{ id:3, lat:35.509817987733584,lng:139.61617335684315},
	{ id:4, lat:35.509704455438865,lng:139.6151218976975 },
	{ id:5, lat:35.509154230274255,lng:139.61444596420856},
	{ id:6, lat:35.50929392935535, lng:139.6116242075418 },
	{ id:7, lat:35.50953845551983, lng:139.61095898793627},
	{ id:8, lat:35.50997509902248, lng:139.60969291095606},
	{ id:9, lat:35.510796030972664,lng:139.6086735567171},
	{ id:10, lat:35.51082220178137, lng:139.60804051507876}
];
//軌跡描画用関数
function disp_polyline(polyline_array){
   var map_obj = $$("map").getMap();
   var flightPath = new google.maps.Polyline({
        path: polyline_array,
        geodesic: true,
        strokeColor: '#FF0000',
        strokeOpacity: 1.0,
        strokeWeight: 2
    });
	flightPath.setMap(map_obj);
}


今回のサンプルでは、マーカをクリックしたとき、メモ情報があれば、そのメモ情報を表示
写真があれば、写真を表示するようにしてみました。
実際には、Webサーバからマーカーの位置情報やメモ情報、画像情報な取得して画面に表示する動作となります。
また、緯度・経度情報は、画面起動後に周期的にGPS情報を自動収集する方式と、手動で、必要なときに取得するモードを準備します。
メモを残したいときや、写真撮影したいときにボタンを押せば、該当場所のGPS情報も収集してデータベースに格納後に、軌跡を閲覧できるような機能に仕上げる必要があります。

以下、ソースコードです。Webixライブラリを使えバ、簡単にGoogleMapとの連携操作が可能になります。

//https://snippet.webix.com/seflatpa
//Googleマップ上にGPS情報を元に、マーカや軌跡を表示するサンプル

///Google マップ用API KEY(事前に申請して取得する必要あり)下記情報は、本サイトでのみ動作可能
// provide your own Google API key
// https://developers.google.com/maps/documentation/javascript/get-api-key
var google_map_api_key = "AIzaSyAi0oVNVO-e603aUY8SILdD4v9bVBkmiTg";
//マップ描画時の中心位置情報
var map_center_info = [ 35.50723278956569, 139.61734275568395 ];
//Google マップ表示尺度
var map_zoom_size = 16;

//メモや写真を記録した地点のGPS情報
//実際には、DBから読み出して設定する
var marker_array =[
{ id:1, lat:35.507853, lng:139.617064, title:"スタート" },
{ id:3, lat:35.509817987733584,lng:139.61617335684315, title:"途中で休憩",info:"memo" },
{ id:7, lat:35.50953845551983, lng:139.61095898793627, title:"撮影2",info:"photo"  },
{ id:9, lat:35.510796030972664,lng:139.6086735567171,title:"もうすぐ到着",info:"memo" },
{ id:10, lat:35.51082220178137, lng:139.60804051507876, title:"終了",info:"photo" }
];


//移動した軌跡配列情報
//実際には、DBから読み出して設定する
 var flightPlanCoordinates = [
	{ id:1, lat:35.507853, lng:139.617064},
	{ id:2, lat:35.508281, lng:139.616763},
	{ id:3, lat:35.509817987733584,lng:139.61617335684315},
	{ id:4, lat:35.509704455438865,lng:139.6151218976975 },
	{ id:5, lat:35.509154230274255,lng:139.61444596420856},
	{ id:6, lat:35.50929392935535, lng:139.6116242075418 },
	{ id:7, lat:35.50953845551983, lng:139.61095898793627},
	{ id:8, lat:35.50997509902248, lng:139.60969291095606},
	{ id:9, lat:35.510796030972664,lng:139.6086735567171},
	{ id:10, lat:35.51082220178137, lng:139.60804051507876}
];

//google map表示
webix.ui({
  rows:[
    {
      view:"toolbar",
      elementsConfig:{
        autowidth:true
      },
      elements:[
        {
          view:"button",
          value:"軌跡表示", 
          click:function(){
            	//軌跡情報をマップに描画
          	   var polyline_array = flightPlanCoordinates;
           	   disp_polyline(polyline_array);
          }
        },
        {
          view:"button",
          value:"全マーカ表示", 
          click:function(){
              //マーカをマップに描画
              marker_array.forEach(function( item ) {
                  $$("map").add(item );
	          });
          }
        },
        {
          view:"button",
          value:"全マーカクリア", 
          click:clearMap
        }, 
        {
          view:"button",
          value:"マーカ表示/非表示",
          click:function(){
            var id_info = 3;
            hideMarker(id_info);
          }
        },
        {
          view:"button",
          value:"マーカ確認",
          click:function(){
            //指定IDのマーカをアニメーションする
          	var id_info = 3;
            animateMarker(id_info);
          }
        }
      ]
    },
    {
      key:google_map_api_key ,
      view:"google-map",
      id:"map",
      zoom:map_zoom_size,
      center:map_center_info,
      data:[]
    }
  ]
});

$$("map").attachEvent("onItemClick", function(id, marker){
    // your code
  if(marker.info == "memo"){
 	 webix.message({type:"success",text:"メモ:"+ marker.title});
  }
  else if(marker.info == "photo"){
    $$("image_view").show();
 	
  }
 });

function img(obj){
  return '<img src="'+obj.src+'" class="content" ondragstart="return false"/>'
}

webix.ui({
  view:"window",
  id:"image_view",
   move:true,
  body:{
    view: "template",
    width:464, height:275,
   template: img,  data:{src:"http://docs.webix.com/samples/26_carousel/imgs/image001.jpg"} 
  },
  head:{
    view:"toolbar", type:"MainBar", elements:[
      {view:"label", label: "撮影写真", align:'left'},
      {view:"button", value:"閉じる", 
          click:function(){
            	$$("image_view").hide();
          }
        },
    ]
  },
  top:80,
  left:20
});


//軌跡描画用関数
function disp_polyline(polyline_array){
   var map_obj = $$("map").getMap();
   var flightPath = new google.maps.Polyline({
        path: polyline_array,
        geodesic: true,
        strokeColor: '#FF0000',
        strokeOpacity: 1.0,
        strokeWeight: 2
    });
	flightPath.setMap(map_obj);
};

function hideMarker(id_info){
  var item = $$("map").getItem(id_info);
  if(!item){
    webix.message({type:"debug",text:"指定マーカが<br>表示されていません。"});
    return;
  }
  item.hidden = !item.hidden;
  $$("map").updateItem( 1, item);
};

function animateMarker(id_info){
  var item = $$("map").getItem(id_info);
  if(!item) {
     webix.message({type:"debug",text:"指定マーカが<br>表示されていません。"});
    return;
  }
  var marker = item.$marker;
  if (marker.getAnimation())
    marker.setAnimation(null);
  else
    marker.setAnimation(google.maps.Animation.BOUNCE);
};

//マーカクリア関数
function clearMap(){
  $$("map").clearAll();
};
 


この記事が気に入ったらサポートをしてみませんか?