リアルタイムの位置情報に基づく拡張現実 Android アプリケーションを開発しています。これは単純な概念です。私のアプリケーションは私の周りのいくつかの場所を表示する必要があります。私はこれを集中的に調査しましたが、まだ問題が発生しています。私は自分の GPS 座標と目的地の GPS 座標を持っています。
私の質問は、携帯電話のカメラが見ているもの (建物など) を取得するにはどうすればよいですか? このような問題を解決する論理的な方法は何ですか?
リアルタイムの位置情報に基づく拡張現実 Android アプリケーションを開発しています。これは単純な概念です。私のアプリケーションは私の周りのいくつかの場所を表示する必要があります。私はこれを集中的に調査しましたが、まだ問題が発生しています。私は自分の GPS 座標と目的地の GPS 座標を持っています。
私の質問は、携帯電話のカメラが見ているもの (建物など) を取得するにはどうすればよいですか? このような問題を解決する論理的な方法は何ですか?
最初に、デバイス内のセンサーの可用性を確認します。デバイスが TYPE_ROTATION_VECTOR をサポートしている場合は、同じセンサー リスナーを登録するか、TYPE_MAGNETIC_FIELD と TYPE_ACCELEROMETER を確認します。
SensorManager mSensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
rSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ROTATION_VECTOR);
if (rSensor == null) {
mSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD);
aSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
}
次に、onSensorChanged 関数で方位角を計算する必要があります。
if (rSensor == null) {
switch (event.sensor.getType()) {
case Sensor.TYPE_MAGNETIC_FIELD:
magnetic = event.values.clone();
break;
case Sensor.TYPE_ACCELEROMETER:
accelerometer = event.values.clone();
break;
}
if (magnetic != null && accelerometer != null) {
Rot = new float[9];
I = new float[9];
SensorManager.getRotationMatrix(Rot, I, accelerometer, magnetic);
float[] outR = new float[9];
SensorManager.remapCoordinateSystem(Rot, SensorManager.AXIS_X,
SensorManager.AXIS_Z, outR);
SensorManager.getOrientation(outR, values);
azimuth = values[0];
magnetic = null;
accelerometer = null;
}
} else {
SensorManager.getRotationMatrixFromVector(mRotationMatrix, event.values);
SensorManager.getOrientation(mRotationMatrix, mValues);
azimuth = Math.toDegrees(mValues[0]));
}
}
この方位角を使用して、カメラビューで位置をプロットできます
double angle = bearing(myLatitude, myLongitude, dLatitude, dLongitude) - azimuth;
double xAxis, yAxis;
if(angle < 0)
angle = (angle+360)%360;
xAxis = Math.sin(Math.toRadians(angle)) * dist;
yAxis = Math.sqrt(Math.pow(dist, 2) - Math.pow(xAxis, 2));
if (angle > 90 && angle < 270)
yAxis *= -1;
double xAxisPosition = angle * (screenWidth / 90d);
xAxis = xAxisPosition - spotImageWidth/2;
float x, y;
if (angle <= 45)
x = (float) ((screenWidth / 2) + xAxis);
else if (angle >= 315)
x = (float) ((screenWidth / 2) - ((screenWidth*4) - xAxis));
else
x = (float) (float)(screenWidth*9);
y = (float)(((screenHeight - 300) - (i * 100)));
protected static double bearing(double lat1, double lon1, double lat2, double lon2) {
double longDiff = Math.toRadians(lon2 - lon1);
double la1 = Math.toRadians(lat1);
double la2 = Math.toRadians(lat2);
double y = Math.sin(longDiff) * Math.cos(la2);
double x = Math.cos(la1) * Math.sin(la2) - Math.sin(la1) * Math.cos(la2) * Math.cos(longDiff);
double result = Math.toDegrees(Math.atan2(y, x));
return (result+360.0d)%360.0d;
}
x, y は、目的地の座標を示します。
必要な最初のステップは、センサーを使用して背面カメラの方向を取得することです。センサーの詳細については、http://developer.android.com/reference/android/hardware/SensorManager.html
を参照
してください。センサーを使用したコーディングが完了したら、戻って次の質問をしてください。
DroidAR SDK https://github.com/bitstars/droidarを試してください。これは Android 用の AR SDK です。あなたの問題のほとんどはそれで解決されるはずです。ビデオマニュアルもあります。プロジェクトに必要なものがいくつかある場合は、コードを調べることもできます。
この問題には、デバイスとターゲットの 2 つの方向性があります。
デバイスの位置の方位角を以下に示します。
この情報は、センサーによって収集できます。ただし、デバイスの向きが固定されていない場合は、次のことを行う必要があります。SensorManager.remapCoordinateSystem
ターゲットへの方位角を以下に示します。
これはおそらく、私がインターネット上で見つけることができる最高の図です。デバイスの位置を取得したら、次の方法でターゲットの位置を計算できます。
azi = Math.abs(Math.toDegrees(Math.atan((tlon-lon)/(tlat-lat))));
ここでtlat
、 とtlon
はターゲットの GPS 位置を示し、lat と lon はデバイスの位置です。この方程式の値は -90 から +90 の範囲にあり、これは実際の方位角ではありません。したがって、3 つの追加コードを追加する必要があります。
if((tlon-lon)>0&&(tlat-lat)<0){
azi = 180 - azi;
}
if((tlon-lon)<0&&(tlat-lat)<0){
azi = 180 + azi;
}
if((tlon-lon)<0&&(tlat-lat)>0){
azi = 360 - azi;
}
これらがすべて完了したら、ターゲットが視界にあるかどうかを簡単に検出できます。
これらがお役に立てば幸いです。