電子国土地図を使ってみる。[Chapter 5]
今回は、OpenLayersのjavascriptの関数に値を渡してみます。
これができると、javascriptと.netとの値の受け渡しができるようになって、vb.net上でOpenLayersのオブジェクトを制御することができます。
codeprojectのVB.NET/C# and JavaScript communicationにjavascriptとの連携について書いてありました。 私が書いているよりも、とても参考になります。
基本的なことは[Chapter 5]で終わります。
今後は、
-
mouse eventの実装
-
shape fileのoverlay(ここが難しそう。。。)
-
平面直角座標系から緯度経度変換
-
rasterのoverlay
-
sqliteの実装
-
spatialiteの実装
-
MapWinGISとの連携
についてアプリケーションの実装を行っていきます。 が、無精なもので。。。
完成はいつになるやら・・・
MapWinGISのwikiも目次だけだし、これについては自分の覚え書き程度で書き留めておかないといけませんな。
準備
今回も、特に準備するものは、ありません。
Visual Basic 2010を使います。(たぶんvb.net2008でも大丈夫でしょう。)
vb.net上で作成した理由は、デスクトップGISとの連携や.net Frameworkでhtmlやxmlを利用したいと考えているからです。
vb.netのデザイン
まずは、vb.netを起動して、適当なプロジェクト名で新規作成します。
使用するコントロールは、Toolstrip,StatusStrip,WebBrowserの3つです。 いつもながらかんたんですな。
デザインイメージ
サンプルコード
Googlemap APIとよく似ているので、簡単にOpenLayersに対応したjavascriptに変更できますね。
短いので、一気にいきます。
コードはこんな感じです。
Imports System Imports System.IO Imports System.Text Imports System.Web Imports System.Xml Imports System.Security.Permissions Public Class Form1 Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load Me.Width = 800 Me.Height = 600 Me.Width = 800 Me.Height = 600 ToolStripButton2.PerformClick() End Sub Private Sub ToolStripButton2_Click(sender As System.Object, e As System.EventArgs) Handles ToolStripButton2.Click 'ObjectForScripting WebBrowser 'コントロールに表示されるWebページ内のスクリプトコードから 'アクセスできるオブジェクトを取得または設定します。 WebBrowser1.ObjectForScripting = New ExtOpenLayersObj 'クラスのインスタンスを渡す '電子国土地図表示 Dim lat As String = ToolStripTextBox1.Text Dim lng As String = ToolStripTextBox2.Text WebBrowser1.DocumentText = kokudoOpenLayers2(Double.Parse(lat), Double.Parse(lng)) End Sub Private Function kokudoOpenLayers2(ByRef lat As Double, ByRef lng As Double) As String Dim txtHtml As String = "" txtHtml = txtHtml & "<html>" & vbCrLf txtHtml = txtHtml & "<head>" & vbCrLf 'txtHtml = txtHtml & "<script type=""text/javascript"" src=""http://openlayers.org/api/OpenLayers.js"" charset=""UTF-8""></script>"& vbCrLf 'txtHtml = txtHtml & "<script type=""text/javascript"" src=""http://portal.cyberjapan.jp/sys/OpenLayers-2.11/OpenLayers.js"" charset=""UTF-8""></script>" & vbCrLf txtHtml = txtHtml & "<script type=""text/javascript"" src=""http://tys-yokohama.com/OpenLayers-2.11/OpenLayers.js"" charset=""UTF-8""></script>" & vbCrLf 'txtHtml = txtHtml & "<script type=""text/javascript"" src=""http://portal.cyberjapan.jp/sys/v4/webtis/webtis_v4.js"" charset=""UTF-8""></script>" & vbCrLf txtHtml = txtHtml & "<script type=""text/javascript"" src=""http://tys-yokohama.com/v4source/webtis_v4.js"" charset=""UTF-8""></script>" & vbCrLf 'txtHtml = txtHtml & "<link rel=""stylesheet"" href=""http://portal.cyberjapan.jp/sys/v4/css/webtis.css"" type=""text/css"">" & vbCrLf txtHtml = txtHtml & "<script type=""text/javascript"">" & vbCrLf txtHtml = txtHtml & "var map = null;" & vbCrLf txtHtml = txtHtml & "var markers = null;" & vbCrLf txtHtml = txtHtml & "var initCX = " & lng.ToString.Trim & ";" & vbCrLf txtHtml = txtHtml & "var initCY = " & lat.ToString.Trim & ";" & vbCrLf txtHtml = txtHtml & "var initZoomLv = 5;" & vbCrLf txtHtml = txtHtml & "var projection900913 = new OpenLayers.Projection(""EPSG:900913"");" & vbCrLf txtHtml = txtHtml & "var projection4326 = new OpenLayers.Projection(""EPSG:4326"");" & vbCrLf txtHtml = txtHtml & "function init(){" & vbCrLf txtHtml = txtHtml & " var maxExtent = new OpenLayers.Bounds(-20037508, -20037508, 20037508, 20037508);" & vbCrLf txtHtml = txtHtml & " var restrictedExtent = maxExtent.clone();" & vbCrLf txtHtml = txtHtml & " var maxResolution = 156543.0339;" & vbCrLf txtHtml = txtHtml & " var options = {" & vbCrLf txtHtml = txtHtml & " controls: [" & vbCrLf txtHtml = txtHtml & " new OpenLayers.Control.Navigation({mouseWheelOptions: {interval: 100}})," & vbCrLf txtHtml = txtHtml & " new OpenLayers.Control.PanZoomBar()," & vbCrLf txtHtml = txtHtml & " new OpenLayers.Control.KeyboardDefaults()," & vbCrLf txtHtml = txtHtml & " new OpenLayers.Control.Attribution()," & vbCrLf txtHtml = txtHtml & " new OpenLayers.Control.OverviewMap()" & vbCrLf txtHtml = txtHtml & " //new OpenLayers.Control.LayerSwitcher()" & vbCrLf txtHtml = txtHtml & " ]," & vbCrLf txtHtml = txtHtml & " projection: projection900913," & vbCrLf txtHtml = txtHtml & " displayProjection: projection4326," & vbCrLf txtHtml = txtHtml & " units: ""m""," & vbCrLf txtHtml = txtHtml & " maxResolution: maxResolution," & vbCrLf txtHtml = txtHtml & " maxExtent: maxExtent," & vbCrLf txtHtml = txtHtml & " restrictedExtent: restrictedExtent" & vbCrLf txtHtml = txtHtml & " };" & vbCrLf txtHtml = txtHtml & " map = new OpenLayers.Map('map', options);" & vbCrLf txtHtml = txtHtml & " map.addControl(new OpenLayers.Control.ScaleLine({maxWidth:200,bottomOutUnits: """" , bottomInUnits: """" ,geodesic:true}));" & vbCrLf txtHtml = txtHtml & " webtisMap = new webtis.Layer.BaseMap(""webtismap"");" & vbCrLf txtHtml = txtHtml & " map.addLayer(webtisMap);" & vbCrLf txtHtml = txtHtml & " map.setCenter(new OpenLayers.LonLat(initCX,initCY).transform(projection4326,projection900913), initZoomLv);" & vbCrLf txtHtml = txtHtml & " // Mapにクリックイベントを登録" & vbCrLf txtHtml = txtHtml & " map.events.register('click', map, onMouseClick);" & vbCrLf txtHtml = txtHtml & " map.events.register('mousemove', map, onMouseMove);" & vbCrLf txtHtml = txtHtml & " markers = new OpenLayers.Layer.Markers( ""Markers"" );" & vbCrLf txtHtml = txtHtml & " map.addLayer(markers);" & vbCrLf txtHtml = txtHtml & "}" & vbCrLf txtHtml = txtHtml & "// mouseclickイベント" & vbCrLf txtHtml = txtHtml & "function onMouseClick(evt) {" & vbCrLf txtHtml = txtHtml & " // クリック地点の座標を取得" & vbCrLf txtHtml = txtHtml & " var lonlat = map.getLonLatFromViewPortPx(evt.xy);" & vbCrLf txtHtml = txtHtml & " // 地図座標に変換" & vbCrLf txtHtml = txtHtml & " lonlat.transform(projection900913, projection4326);" & vbCrLf txtHtml = txtHtml & " document.sample.boxLon.value = lonlat.lon;" & vbCrLf txtHtml = txtHtml & " document.sample.boxLat.value = lonlat.lat;" & vbCrLf '.NETのSubroutineを呼び出す。 txtHtml = txtHtml & " window.external.MouseClick(lonlat.lat, lonlat.lon);" & vbCrLf txtHtml = txtHtml & "}" & vbCrLf txtHtml = txtHtml & "// mousemoveイベント" & vbCrLf txtHtml = txtHtml & "function onMouseMove(evt) {" & vbCrLf txtHtml = txtHtml & " var lonlat = map.getLonLatFromViewPortPx(evt.xy);" & vbCrLf txtHtml = txtHtml & " // 地図座標に変換" & vbCrLf txtHtml = txtHtml & " lonlat.transform(projection900913, projection4326);" & vbCrLf '.NETのSubroutineを呼び出す。 txtHtml = txtHtml & " window.external.MouseMove(lonlat.lat, lonlat.lon);" & vbCrLf txtHtml = txtHtml & "}" & vbCrLf 'Markerの描画 txtHtml = txtHtml & "// mousemoveイベント" & vbCrLf txtHtml = txtHtml & "function moveToPoint(Lat, Lng, strTitle) {" & vbCrLf txtHtml = txtHtml & " var lonlat = new OpenLayers.LonLat(Lng,Lat).transform(projection4326,projection900913);" & vbCrLf txtHtml = txtHtml & " map.setCenter(lonlat);" & vbCrLf txtHtml = txtHtml & " // markerの描画" & vbCrLf txtHtml = txtHtml & " var marker = new OpenLayers.Marker(lonlat);" & vbCrLf txtHtml = txtHtml & " markers.addMarker(marker);" & vbCrLf txtHtml = txtHtml & "}" & vbCrLf txtHtml = txtHtml & "</script>" & vbCrLf txtHtml = txtHtml & "</head>" & vbCrLf txtHtml = txtHtml & "<body onload=""init();"">" & vbCrLf txtHtml = txtHtml & "<div id=""map"" name=""map"" style=""width: 100%; height:80%;""></div>" & vbCrLf txtHtml = txtHtml & "<form name=""sample"">" & vbCrLf txtHtml = txtHtml & "<div>チェックのためのhtml出力</div>" & vbCrLf txtHtml = txtHtml & "<div>" & vbCrLf txtHtml = txtHtml & "緯度:<input type=""text"" name=""boxLat"" />" & vbCrLf txtHtml = txtHtml & "経度:<input type=""text"" name=""boxLon"" />" & vbCrLf txtHtml = txtHtml & "</div>" & vbCrLf txtHtml = txtHtml & "</form>" & vbCrLf txtHtml = txtHtml & "</body>" & vbCrLf txtHtml = txtHtml & "</html>" & vbCrLf kokudoOpenLayers2 = txtHtml End Function Private Sub ToolStripButton1_Click(sender As System.Object, e As System.EventArgs) Handles ToolStripButton1.Click 'ポイント移動ボタン WebBrowser1.Document.InvokeScript("moveToPoint", _ {CDbl(ToolStripTextBox1.Text), _ CDbl(ToolStripTextBox2.Text), _ CStr(ToolStripTextBox3.Text)}) End Sub End Class <PermissionSet(SecurityAction.Demand, Name:="FullTrust")> _ <System.Runtime.InteropServices.ComVisibleAttribute(True)> _ Public Class ExtOpenLayersObj Public Sub MouseClick(ByVal lat As Double, ByVal lng As Double) MsgBox("OpenLayers" & vbCrLf & _ "緯度:" & Format(lat, "###.######").ToString & vbCrLf & _ "経度:" & Format(lng, "###.######").ToString, MsgBoxStyle.OkOnly, _ "OpenLayersから取得") 'Form1.ToolStripStatusLabel2.Text = Format(lat, "###.######").ToString 'Form1.ToolStripStatusLabel4.Text = Format(lng, "###.######").ToString End Sub Public Sub MouseMove(ByVal lat As Double, ByVal lng As Double) 'MsgBox("Googlemap" & vbCrLf & _ ' "緯度:" & lat.ToString & vbCrLf & _ ' "経度:" & lng.ToString, MsgBoxStyle.OkOnly, "Javascriptから取得") Form1.ToolStripStatusLabel2.Text = Format(lat, "###.######").ToString Form1.ToolStripStatusLabel4.Text = Format(lng, "###.######").ToString End Sub End Class
プログラムの説明
注意点jacascriptを弊社のURLに設置して呼び出しています。 この部分は、本家を参照してください。 弊社のSercerのdirectory構成で変更になる可能性があります。
プログラムとしては、
-
javascriptから呼び出すExternalGMapObjクラスを作成して、その中でMouseClickとMouseMove subroutineを作成しておきます。
-
「window.external.[VBのパブリックルーチン]」で.NETのpublic subroutineを呼び出します。
-
javascript側でfunction moveToPointを作成して、処理をプログラムします。
-
.net側で「ポイント移動」ボタンをクリックした場合の処理をプログラムします。
簡単にjavascriptの関数に.NET側の値に渡すことができました。
プログラムの実行
それでは、実行してみましょう。
プログラムを起動すると地図が表示されます。
「ポイント移動」ボタンをクリックした場合、toolstrip内のtextboxの緯度経度に移動して、マーカーが描画されます。 Googlemapのサンプルと同じようにタイトルを入力しても、tooltipsでマーカーにmouseoverすると表示されません。ここのところは、作成中です。
指定した緯度経度にmarkerを描画した例
基本的は機能だけをチェックしてみましたが、いろいろと応用すれば、非常におもしろいソフトウェアができあがりますね。
サンプルコードをこちらにアップしておきます。使用する際は自己責任にて使って下さい。
それでは、今回の.NETで電子国土地図を使ってみるシリーズは、終了します。
参考までに
参照したHP(先人に感謝します。
最近のコメント