PLATEAU SDK for Unityを試してみる
環境
- Windows11
- Unity2021.3.8f1
- PLATEAU SDK for Unity v0.5.1
現時点ではARM系CPUは未対応とのこと
次のリポジトリのReleasesからtarball形式のunitypackageをダウンロード
UnityのPackage Managerの Add package from tarball
からインポート
都市データのインポートは「ローカル」と「サーバー」から行うことが可能だが、 現時点ではローカルのみ対応。
都市データはG空間情報センターのPLATEAUポータルサイト からダウンロードする
- 入力フォルダには、直下に
udx
フォルダを持つパスを指定する - 基準座標系には利用する都市に最も近い地域を選ぶ
↑を選択したら、範囲選択へ
シーンビューに地理院地図が表示された。
ここからインポートするモデルの範囲を選択する。
とりあえず渋谷駅周りを選択した。
インポートする都市情報を選択できる画面が出てきた。
とりあえずデフォルトのまま全部インポート開始。
非同期でインポートされている。
ちなみに、 変換元のファイルはすべてStreamingAssets/.PLATEAU
下にコピーされている(Unityからは見えない隠しフォルダ)。
一部ファイルのパースに失敗していたが、建物はすべて変換された。
変換されたオブジェクトのトップにPLATEAUInstancedCityModel
コンポーネントがアタッチされており、緯度経度などが確認できる。
都市情報へアクセスするサンプル
タップした建物を都市情報を画面上へ表示するというもの
タップしたときにインポート済みのCityGMLファイルをパースして都市情報を取得している。
Geospatial APIと組み合わせるときに、 これまではPlateauCityGmlSharpでCityGMLからヘッダーに座標を埋め込んだobjに変換して使ってたところを入れ替えたい
Androidで実行時にこの位置情報を使いたいんだけどDllNotFoundException
出てる。
using var geoRef = _plateauInstancedCityModelPrefab.GeoReference;
var geoCoord = geoRef.Unproject(new PlateauVector3d(0, 0, 0));
// geoCoord.Latitude で緯度がとれるはず...
Exception: DllNotFoundException: Unable to load DLL 'plateau'. Tried the load the following dynamic libraries: Unable to load dynamic library 'plateau' because of 'Failed to open the requested dynamic library (0x06000000) dlerror() = dlopen failed: library "plateau" not found
PLATEAU.Interop.NativeMethods.plateau_create_geo_reference (System.IntPtr& outGeoReferencePtr, PLATEAU.Interop.PlateauVector3d referencePoint, System.Single unitScale, PLATEAU.Geometries.CoordinateSystem coordinateSystem, System.Int32 zoneId) (at <00000000000000000000000000000000>:0)
PLATEAU.Geometries.GeoReference..ctor (PLATEAU.Interop.PlateauVector3d referencePoint, System.Single unitScale, PLATEAU.Geometries.CoordinateSystem coordinateSystem, System.Int32 zoneID) (at <00000000000000000000000000000000>:0)
PLATEAU.CityInfo.PLATEAUInstancedCityModel.get_GeoReference () (at <00000000000000000000000000000000>:0)
CityExtension.Scripts.Tests.Runtime.PlacePlateauByGeospatialTest.Start () (at <00000000000000000000000000000000>:0)
System.Threading.ExecutionContext.RunInternal (System.Threading.ExecutionContext executionContext, System.Threading.ContextCallback callback, System.Object state,
これのことでエディタ専用かな
何も考えずにGeospatial APIのTerrain Anchorで配置してみたけど高さがずれた。
緯度・経度・地表からの高さにはPLATEAUInstancedCityModel
のインスペクターに表示されていたものをそのまま写してる。
東京湾海水面ってなんだっけ
東京湾海水面は標高0mのこと
Terrain Anchor使わずに通常のアンカーを使うなら、 楕円体高を渡すのでジオイド高だけ渡せばよさそう
楕円体高 = 標高(0) + ジオイド高
だいたいこんな処理
まだモデルはインポートしたあとシーンに置きっぱなしなので、 Geospatial Anchorを生成したら親子関係を整理する形
あとでSDKのエクスポート機能を試したら、Prefab状態のモデルを動的に生成するとかやると思う
// PLATEAUInstancedCityModelの位置に書かれていた基準位置をとりあえずベタ書き
var lat = 35.645d;
var lng = 139.695d;
// 高さ(標高)は0m
// 国土地理院のAPIからジオイドをリクエスト
var geoid = await GsiClient.Instance.RequestGeoidHeight(lat, lng);
var anchor = GeospatialManager.Instance.RequestGeospatialAnchor(new GeospatialPose
{
Latitude = lat,
Longitude = lng,
Altitude = geoid.value
}, terrain: false);
// PLATEAUのモデルはシーンに置きっぱなしにしてあるので、親子関係を整理してローカル座標など初期化
if (_plateauInstancedCityModel != null)
{
_plateauInstancedCityModel.transform.SetParent(anchor.transform);
_plateauInstancedCityModel.transform.localPosition = Vector3.zero;
_plateauInstancedCityModel.transform.localRotation = Quaternion.identity;
}