7

我的应用程序中有一个活动,其中有我用作地图的图像。如果图像与谷歌地图“网格对齐”,那么当我使用从 googlemaps 在线获得的地图的左上角和右下角时,我可以将用户 gps 转换为屏幕上的 x 和 y。但是,如果地图不是“网格对齐”并且与我的数学返回的值成一定角度,则会将用户的位置绘制在屏幕外。显然我错过了如何处理地图角度的部分,所以如果有人能阐明如何做到这一点,那将是非常有帮助的。

我知道我必须计算出弧度的角度并进行一些转换,但我不知道从哪里开始。到目前为止,这就是我用来在画布上绘制 x 和 y 的方法。

public double[] getPositionGPS(Location upperLeft, Location lowerRight, Location current){

    try{

        double hypotenuse = upperLeft.distanceTo(current);
        double bearing = upperLeft.bearingTo(current);
        double currentDistanceY = Math.cos(bearing * Math.PI / OneEightyDeg) * hypotenuse;
        //                           "percentage to mark the position"
        double totalHypotenuse = upperLeft.distanceTo(lowerRight);
        double totalDistanceY = totalHypotenuse * Math.cos(upperLeft.bearingTo(lowerRight) * Math.PI / OneEightyDeg);
        double currentPixelY = currentDistanceY / totalDistanceY * ImageSizeH;

        double hypotenuse2 = upperLeft.distanceTo(current);
        double bearing2 = upperLeft.bearingTo(current);
        double currentDistanceX = Math.sin(bearing2 * Math.PI / OneEightyDeg) * hypotenuse2;
        //                           "percentage to mark the position"
        double totalHypotenuse2 = upperLeft.distanceTo(lowerRight);
        double totalDistanceX = totalHypotenuse2 * Math.sin(upperLeft.bearingTo(lowerRight) * Math.PI / OneEightyDeg);
        double currentPixelX = currentDistanceX / totalDistanceX * ImageSizeW;

        return new double[]{currentPixelX, currentPixelY};

    }catch(Exception e){

        e.printStackTrace();
        return new double[]{0,0};

    }
4

5 回答 5

2

首先,将您的谷歌地图坐标映射到您的自定义图像,就好像图像没有倾斜一样。在这里,您基本上是在处理缩放和偏移。假设你得到的坐标是(x, y).

然后,根据这个矩阵旋转你的坐标:围绕原点旋转一个点。由于您已经知道角度,因此您知道/可以计算自定义地图旋转的中心点坐标。假设它是(a, b). 具体来说:

1)将您的地图坐标(x, y)转换为(0,0)基于坐标(x-a, y-b),,

2)使用该矩阵旋转,你有一个新的坐标(x', y')

3) 将其转回(a, b)基于坐标,(x'+a, y'+b).

于 2013-11-04T13:21:28.547 回答
1

我可能完全错了,但我认为这是一种获得旋转角度(或者可能是 4 个角)的方法:

  1. 获取lowerRight 和 upperLeft 之间的角度alpha 。我猜这等于180 - lowerRight.bearingTo(upperLeft) 编辑(这个等式应该取决于屏幕的象限)
  2. 使用您的 X、Y(屏幕)坐标来获取斜边和下边缘之间的角度theta 。我想(再次)这个角度的正弦等于:(height) / ((height^2) + (width^2))^1/2
  3. 现在旋转角度等于theta - alpha

如果你想形象化这个:

布拉

于 2013-11-08T10:58:03.657 回答
0

我不确定我是否理解您的问题,但是您不能像这样从 API 中获取 (X, Y) 位置吗?

// myMap is a GoogleMap instance and location is a Location instance
Projection projection = myMap.getProjection();
LatLng latlng = new LatLng(location.getLatitude(), location.getLongitude());
Point pointInTheScreen = projection.toScreenLocation(latlng);

有关详细信息,请参阅GoogleMap API。

于 2013-11-04T12:45:10.137 回答
0

是的,您可以绘制不在可见地图上的点。通过设置 LatLngBounds 来解决这个问题。然后显示 LatLngBounds 的地图。您还可以移动地图以显示 LatLngBounds。这里没有什么棘手的问题,没有切线、斜坡或地球的双曲线曲率。所有这些都以度数为单位,所以不要过度考虑你的解决方案。如果你转动地图,点就会随之转动。因此,将您的点添加到地图上,找到边界并倾斜相机。将相机向后倾斜,所有点仍将在屏幕上!这将使您开始了解屏幕上的所有点。

与示例获取对谷歌地图的引用相同。

private void setUpMapIfNeeded() {
    // Do a null check to confirm that we have not already instantiated the
    // map.

    if (mMap == null) {
        // Try to obtain the map from the SupportMapFragment.
        // mMap = mMapFragment.getMap();
        // // Check if we were successful in obtaining the map.

        // Try to obtain the map from the SupportMapFragment.
        mMap = ((SupportMapFragment) getSupportFragmentManager()
                .findFragmentById(R.id.map)).getMap();
        // use the settings maptype

        // Check if we were successful in obtaining the map.
        if (mMap != null) {
            setUpMap();
        }
    }
}

让我们开始寻找地图的边界。

import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.LatLngBounds;

LatLngBounds 和 LatLngBounds.Builder 的字段

private LatLngBounds bounds;
private LatLngBounds.Builder myLatLngBuilder;

初始化 LatLngBounds.Builder

myLatLngBuilder = new LatLngBounds.Builder();

对于地图上的每个点。

LatLng myLatLng = new LatLng(latitude, longitude);
myLatLngBuilder.include(myLatLng);

然后,当您完成添加点时,建立您的边界。

bounds = myLatLngBuilder.build();

现在我有了地图上所有点的边界,我可以只显示地图的那个区域。我从地图样本中提取的这段代码。

final View mapView = getSupportFragmentManager().findFragmentById(
            R.id.map).getView();
    if (mapView.getViewTreeObserver().isAlive()) {
        mapView.getViewTreeObserver().addOnGlobalLayoutListener(
                new OnGlobalLayoutListener() {
                    @SuppressWarnings("deprecation")
                    // We use the new method when supported
                    @SuppressLint("NewApi")
                    // We check which build version we are using.
                    @Override
                    public void onGlobalLayout() {
                        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
                            mapView.getViewTreeObserver()
                                    .removeGlobalOnLayoutListener(this);
                        } else {
                            mapView.getViewTreeObserver()
                                    .removeOnGlobalLayoutListener(this);
                        }
                        mMap.moveCamera(CameraUpdateFactory
                                .newLatLngBounds(bounds, 50));
                    }
                });
    }

这基本上就是我的应用程序Bestrides KML Reader显示地图的方式,因此屏幕上没有任何点。

祝你好运丹尼117

于 2013-11-08T02:03:43.457 回答
-1

您可以使用磁场传感器(又名指南针)来获取设备的方向,然后将您的自定义视图“网格对齐”到您的地图。

于 2013-11-07T12:56:58.930 回答