Upgrade to Pro — share decks privately, control downloads, hide ads and more …

HCL Nomad で GPS を使おう!

HCL Nomad で GPS を使おう!

HCL Nomad は、HCL Notes/Domino 用に作成したアプリケーションをスマートフォンやタブレットで利用するためのアプリです。言わば「スマホ版Notesクライアント」です。
この資料では LotusScript に新たに追加された GPS を利用するためのクラスの使い方をはじめ、HCL Nomad で GPS 関連クラスを使用する際の挙動や Notes アプリとしての活用方法などに触れます。

2020年6月開催の「テクてくLotus技術者夜会」で使用した資料です。

Haruyuki Nakano

September 01, 2022
Tweet

More Decks by Haruyuki Nakano

Other Decks in Programming

Transcript

  1. NotesGPS クラス 位置情報へのアクセスを提供します。1.0.4 以降の HCL Nomad をサポートしています。 包含関係 スーパークラス: NotesSession

    サブクラス: NotesGPSPosition プロパティ TimeoutSec ... NotesGPS 要求のタイムアウト(秒)。デフォルトは9秒(プラットフォームに依存) HighAccuracy ... 高精度の位置だけ返すようプラットフォームに指示します。屋内では使用できませ ん。 メソッド GetCurrentPosition ... プラットフォームに要求を送信して、現在の位置を取得します。 RequestAccess ... プラットフォームからのアクセスを要求します。アクセスが提供される場合 True を 戻します。
  2. HighAccuracy プロパティ • GetCurrentPosition メソッドまたは Update メソッドをコールすると最後に返された GPS 座標のタイムスタンプをチェックします。この時、タイムスタンプが古すぎる場合、GPS は新しい座標を取得しようとします。「古すぎる」の定義は次のとおりです。

    • 高精度(HighAccuracy = True):15秒前 • 低精度(HighAccuracy = False):1分前 • iOS のGPS radio に設定されている目的の精度に影響します。 • 高精度:10m以内の位置を取得しようとする • 低精度:最も近い100m以内の位置を取得しようとする • GPS が使用するバッテリーの量に影響します。 • 高精度>低精度
  3. NotesGPSPosition クラス 現在の位置情報を含みます。1.0.4 以降の HCL Nomad をサポートしています。 包含関係 スーパークラス: NotesGPS

    サブクラス: NotesGPSCoordinates プロパティ Coordinates ... 位置情報へアクセスします TimeStamp ... 最後に位置情報を取得した時刻です。NotesDateTime オブジェクトを返します。 メソッド Update ... プラットフォームに要求を送信して、現在の位置を取得します
  4. NotesGPSCoordinates クラス デバイスの位置の現在の座標を含みます。1.0.4 以降の HCL Nomad をサポートしています。 包含関係 スーパークラス: NotesGPSPosition

    プロパティ Accuracy ... 緯度経度の誤差。単位はm。 Altitude ... 高度。単位はm。負の値は無効。 AltitudeAccuracy ... 高度の誤差。単位はm。 Heading ... 現在の向きを真北から始まる角度で示す。単位は度。北は0、東は90、南は180度。 負の値は無効。 Latitude ... 緯度。 Longitude ... 経度。 Speed ... 速度。単位は秒速(m/s)。負の値は無効。
  5. GPSから位置情報を取得する Dim ss As New NotesSession Dim gps As NotesGPS

    Dim position As NotesGPSPosition Dim coordinates As NotesGPSCoordinates Dim msg$, crlf$ crlf = Chr(10) Set gps = ss.CreateGPS Set position = gps.GetCurrentPosition Set coordinates = position.Coordinates With coordinates msg = "緯度: " & .Latitude & _ crlf & "経度: " & .Longitude & _ crlf & "高度: " & .Altitude & _ crlf & “方角: " & .Heading & _ crlf & "速度: " & .Speed & _ crlf & "緯度経度の誤差: " & .Accuracy & _ crlf & "高度の誤差: " & .AltitudeAccuracy End With Messagebox msg
  6. Function reverseGeocoding( lat As Double, lng As Double ) As

    String Dim ss As New NotesSession Dim req As NotesHTTPRequest Dim nav As NotesJSONNavigator Dim elm As NotesJSONElement Dim arr As NotesJSONArray Dim obj As NotesJSONObject Dim url$ Const API_KEY = “xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" url = "https://maps.googleapis.com/maps/api/geocode/json?latlng=" & lat & "," & lng & "&language=ja&key=" & API_KEY Set req = ss.CreateHTTPRequest req.PreferJSONNavigator = True req.SetHeaderField "Content-Type", "application/json" Set nav = req.Get( url ) Set elm = nav.GetElementByName( "results" ) Set arr = elm.Value Set elm = arr.GetFirstElement Set obj = elm.Value Set elm = obj.GetElementByName( "formatted_address" ) reverseGeocoding = elm.Value End Function 緯度と経度を入力して、住所を出力する Google Maps API 戻り値から最初の住所を抽出
  7. 球面三角法 Function spherical_trigonometry( lat1 As Double, lng1 As Double, lat2

    As Double, lng2 As Double ) As Double Dim radLat1 As Double, radLng1 As Double ‘地点1 Dim radLat2 As Double, radLng2 As Double ‘地点2 Dim averageLat As Double, averageLng As Double Dim c As Double Const r = 6378137.0 '赤道半径 c = 180 / Pi '1周を360とする60分法からラジアンへ変換する際に使用する。(360/2πを約 分) ' 円弧の長さを扱うため、角度(緯度経度)をラジアンへ変換 radLat1 = lat1 / c radLng1 = lng1 / c radLat2 = lat2 / c radLng2 = lng2 / c averageLat = (radLat1 - radLat2) / 2 averageLng = (radLng1 - radLng2) / 2 spherical_trigonometry = r * 2 * Asin( Sqr( Sin( averageLat ) ^ 2 + Cos( radLat1 ) * Cos( radLat2 ) * Sin( averageLng ) ^ 2 ) ) End Function ヒュベニイ(Hubeny)の式 Function hubeny( lat1 As Double, lng1 As Double, lat2 As Double, lng2 As Double ) As Double Dim dLat As Double, dLng As Double Dim i As Double, W As Double, M As Double, N As Double Const E2 = 6.69437999019758E-03 '第2離心率(e^2) Const r = 6378137.0 '赤道半径 dLat = lat2 - lat1 dLng = lng2 - lng1 i = ( lat1 + lat2 ) / 2 W = Sqr( 1 - E2 * Sin( i * Pi / 180 ) ^ 2 ) M = r * ( 1 - E2 ) / W ^ 3 N = r * W hubeny = Sqr( ( dLat * Pi / 180 * M ) ^ 2 + ( dLng * Pi / 180 * N * Cos( i * Pi / 180 ) ) ^ 2 ) End Function
  8. Dim ss As New NotesSession Dim dc As NotesDocumentCollection Dim

    doc As NotesDocument Dim lat1 As Double, lng1 As Double Dim lat2 As Double, lng2 As Double Dim distance As Double Set dc = ss.CurrentDatabase.UnprocessedDocuments Set doc = dc.GetFirstDocument lat1 = doc.GetItemValue("Latitude")(0) lng1 = doc.GetItemValue("Longitude")(0) Set doc = dc.GetNextDocument( doc ) lat2 = doc.GetItemValue("Latitude")(0) lng2 = doc.GetItemValue("Longitude")(0) distance = spherical_trigonometry(lat1, lng1, lat2, lng2) Messagebox distance & " m",,"球面三角法による2地点間の距離" ビューで選択している2つの 文書を取得し、それぞれに保 存されている位置情報から距 離を算出して表示する
  9. Dim prefix$, suffix$, kml$ prefix = |<?xml version="1.0" encoding="UTF-8"?> <kml

    xmlns="http://www.opengis.net/kml/2.2"> <Document> <name>GPS LOG</name> <description>KMLサンプル</description> <Style id="blueLine"> <LineStyle> <color>7fff00ff</color> <width>4</width> </LineStyle> </Style> <Placemark> <name>GPS LOG</name> <description>KML サンプル</description> <styleUrl>#blueLine</styleUrl> <LineString> <extrude>1</extrude> <tessellate>1</tessellate> <altitudeMode>absolute</altitudeMode> <coordinates>| suffix = |</coordinates> </LineString> </Placemark> </Document> </kml>| kml = prefix & root & suffix Dim ss As New NotesSession Dim dc As NotesDocumentCollection Dim doc As NotesDocument Dim unid$ Set dc = ss.Currentdatabase.Unprocesseddocuments Set doc = dc.Getfirstdocument() unid = doc.Getitemvalue("unid")(0) Set dc = Nothing Set doc = Nothing Dim vw As NotesView Dim nav As NotesViewNavigator Dim ent As NotesViewEntry Dim root$ Set vw = ss.Currentdatabase.Getview( "byunid" ) Set nav = vw.Createviewnavfromcategory( unid ) Set ent = nav.Getfirst() While Not ent Is Nothing root = root & ent.Columnvalues( 2 ) & _ "," & ent.Columnvalues( 3 ) & _ "," & ent.Columnvalues( 4 ) & Chr(10) Set ent = nav.Getnext( ent ) Wend 'KMLファイルを保存する Dim filepath$, platform$, dlm$ Dim stream As NotesStream platform = LCase( ss.Platform ) If platform = "ios" Then dlm = "/" ElseIf platform = "windows/32" Then dlm = "¥" End If filepath = ss.Getenvironmentstring( "Directory", True ) filepath = filepath & dlm & "kml.kml" Set stream = ss.Createstream() If Not stream.Open( filepath, "UTF-8" ) Then MessageBox "KMLファイルが開きません。",,"Open Failed" Exit sub End If If stream.Bytes <> 0 Then Call stream.Truncate() End If Call stream.Writetext( kml, EOL_CRLF ) Call stream.Close() KMLファイルを作成する ビューから取得した位置情 報(緯度、経度、高度)をカ ンマで区切った1行の文字 列にして、複数の位置情報 を改行で区切り、変数 root へ格納する 変数 kml の内容を データディレクトリの .kml ファイルへ書き出す 変数 root を 変数 prefix と suffix で挟み、変数 kml へ格納する
  10. 座標(緯度経度)の取得と更新 • NotesGPSPosition.Coordinates をコールするだけでは最新の位置情報を取得できません。最新の位置情報を得る には GetCurrentPosition または Update をコールします。どちらも同じ位置情報を返します。 •

    現在の更新された位置情報を取得したい場合、既に有効な NotesGPSPosition オブジェクトがあれば Update をコー ルすることができます。Update をコールすれば GetCurrentPosition をコールして NotesGPSPosition オブジェ クトを再初期化する手間を回避できます。 • GetCurrentPosition と Update のコールでは TimeStamp をチェックします。メモリ内(GPSロケーションストリー ム)に有効な位置情報が無い場合、 または TimeStamp が古すぎる場合(高精度:15秒前、低精度:1分前)、新しい位置情 報を取得しようとします。 • GPSが位置情報を取得しようとしている間、LotusScript コードは TimeoutSec で指定した時間(iOSは最大10秒)待 機します。時間内に新しい位置情報を得られるとその場所を返しますが、そうでなければ「リクエストタイムアウト前にGPS 位置情報を取得できません」というメッセージをユーザーへのアラートとして返します。 • 現在、新しい位置情報の取得に失敗したときに試行する回数は指定できません。(将来の機能拡張に期待!)
  11. 電力の消費 • GetCurrentPosition が最初にコールされたとき iOS側でGPSロケーションストリームが開始され、タイマーが作動して GPS radio が3 分間オンのままになります。GPS radio

    がオンの間、Nomad は追加の電力を消費します。 • GPSロケーションストリームを終了すると GPS radio はオフになりますが、現在 LotusScript から GPS radio をオフにする方法はあり ません。LotusScript を終了しても3分のタイマーが終了するまで GPS radio はオンのままです。Nomad がシャットオフされると GPS radio はそれを呼び出していたアプリがシャットオフされたことを自動的に認識し、GPS radio をオフにします。 • GPS radio は3分間オンのままになりますが、GetCurrentPosition または Update のコールごとに3分の継続時間が更新されます。 どちらのメソッドも電力の消費量は同じです。 • GPS radio がオンの間、 LotusScriptが新しい情報を要求しない場合でも、デバイスの電力を消費します。 • GPS radio がオンの間、Apple Maps のような他のロケーション志向アプリに匹敵する追加の電力を消費すると予想できます。 • 低精度(HighAccuracy=False)を使用する(または精度を設定しない)とき、GPSが使用するバッテリーの量を抑えることができます。 • 現在、GPS radio をオンの状態に保つ(GPSロケーションストリームが開いている)時間を変更することはできません。(将来の機能拡張に期 待!)
  12. 現状の制限など(2020年6月時点) • GPSへのアクセスは、LotusScript のみサポートしています。Java では使用できません。 • Nomad は、標準装備の OS API

    を使い、モバイルデバイスにある GPS センサーへアクセスします。 現状は、コンピュータの USB ポートに接続された GPS デバイスをサポートしていません。したがって コードのテストやデバッグは、モバイルデバイス上の Nomad で行う必要があります。 • Heading と Speed の値は、必要な頻度で更新されない場合があります。他にもタイムアウトした後 に返すメッセージが正しくない不具合もありますが、これらの問題はNomadチームのバックログにあ ります。 • iOSでは NotesGPS.TimeoutSec の最大値は9(秒)です。これはiOSでの制限としてNomadの 文書に記載されている制限(10秒)と同じです。 10(秒)以上の値を指定しても9秒に短縮されます。ト ラブル予防のためインターバルを設け、9秒としています。
  13. 【GPSに関するブログ記事】 Nomad で GPS を使う GPS ロガー的なアプリを作ってみた 【HCL Nomad に関するブログ記事】

    Notes で QR コードを表示しよう Notes データベースを開くショートカットを iPad のホーム画面へ追 加する Nomad でも OCR iPhone? iPad? @Platform の拡張について 本日ご紹介したサンプルをまとめた データベース GPSTools.nsf を公開しました! https://bit.ly/3dcEKkd