Unity实用功能之经纬度和Unity坐标之间转换| 8月更文挑战

概述

在作模拟仿真的项目时,有时候须要加载地图上某一块的地貌和建筑,这时候咱们只知道这些建筑在地图上的经纬度坐标,并不知道其在Unity中的世界坐标,那么如何才能将全部建筑按照真实地图显示出来就成了一个问题,本篇文章主要介绍的就是,如何经过经纬度,计算出其在Unity中的世界坐标。markdown

注:由于Unity中的Vector3是float,因此本文中使用的是float类型的数据,精准度会有些许误差,若是对精准度要求比较高,还请本身重写下Unity的Vector,将其重写为double类型的,在换算过程当中我将使用double,只是最后返回值得时候会转成float。spa

思路分析

经纬度组合起来就是一个Vector2类型的数据。咱们首先在Unity中建立两个点,两个点的位置就是一个正方形(长方形等)的对角线的位置便可,分别在地图上找到两个点的经纬度,也就是使用这两点,在地图上圈出来一个范围,将找到的这个两个点的经纬度,分别赋给在Unity中建立的两个点,这样咱们在Unity中的范围位置,就和显示地图中的位置相对应了起来,在经过其坐标的X,Z轴的值和经纬度的差值,从而计算出坐标。具体示意图以下:3d

image.png

image.png 上图中,只要将图二中的AB点的经纬度,赋值给图一种AB点,便可经过坐标差,实时计算出由AB两点组成的正方形内的全部点的坐标code

功能实现

上图中两个球就是肯定位置的关键点。若是这两个点都没有肯定好,那么一切都是白扯。 说通俗一点就是,已知A,B的位置和对应的数值,和 C 的位置,让你求 C 对应的值,是一个道理。 而咱们在程序中们能够使用动态设置这两个定位点的位置,而不用一遍遍使用手动调节。orm

在程序中,咱们还能够经过获取中心点的经纬度,经过向左右加减的方式,肯定两角的坐标,这样作的好处就是不管是什么样的经纬度均可以计算出,而且不超出定位点单的范围。it

首先进行程序的初始化,先肯定两个定位点的坐标,以及两个坐标点在Unity中的经纬度的差io

//本案例中是直接肯定经纬度,不是经过中间点加减肯定的
//点1
BottomRightSai = new Vector2(113.98071f, 22.52864f);
//点2
TopLeftSai = new Vector2(80.15071f, 40.56864f);
z_offset = BottomRightSai.y - TopLeftSai.y;//地图中的维度差  
x_offset = BottomRightSai.x - TopLeftSai.x;//地图中的经度差  
z_w_offset = BottomRightPoint.position.z - TopLeftPoint.position.z;//unity中的维度差  
x_w_offset = BottomRightPoint.position.x - TopLeftPoint.position.x;//unity中的经度差
复制代码

接下来是经过已知的经纬度,计算出该点在Unity中的坐标table

注:此方法无法计算出在Unity中的高度,全部物体的Y轴是固定的,同定位点。若是想要使用高度,须要Unity读取灰度图才可以获取到高度class

/// <summary>
    /// 由经纬度获得位置点  
    /// </summary>
    /// <param name="se"></param>
    /// <returns></returns>
    public Vector3 GetWorldPoint(Vector2 se)
    {
        double tempX = se.x - TopLeftSai.x;
        double tempZ = se.y - BottomRightSai.y;
        double _tempX = (tempX * x_w_offset / x_offset + TopLeftPoint.position.x);//计算X轴
        double _tempZ = (tempZ * z_w_offset / z_offset + BottomRightPoint.position.z);//计算Z轴
        //获取该点世界坐标
        return new Vector3((float)_tempX, 0, (float)_tempZ);
    }
复制代码

由Unity坐标逆推经纬度一样的原理,仍是上面提到的问题,经纬度通常都是double数据,此方法中使用的是float,精准度会有误差,若是定位点范围较大可能不会有大影响,可是范围若是很小误差可能会比较明显import

/// <summary>
    /// 由位置点获得经纬度  
    /// </summary>
    /// <param name="curPoint"></param>
    /// <returns></returns>
    public Vector3 GetLatLon(Vector3 curPoint)
    {
        //坐标误差
        double _x_offset = (curPoint.x - BottomRightPoint.position.x) * x_offset / x_w_offset;
        double _z_offset = (curPoint.z - TopLeftPoint.position.z) * z_offset / z_w_offset;
        double resultX = _x_offset + BottomRightSai.x;
        double resultZ = _z_offset + TopLeftSai.y;
        return new Vector2((float)resultX, (float)resultZ);
    }
复制代码

到这里在Unity中经纬度转和世界坐标互转的功能就实现了,若是还有不明白的能够多研究下代码,其实原理仍是很好理解的,案例源代码会在以后整理好以后放出。

注意

此案例功能比较单一,精准度因为float和double之间的转换,会有些许误差,介意的同窗请绕道。

写在最后

总体项目案例会在后期整理好以后分享给你们,若有错误之处还请多多指出。

相关文章
相关标签/搜索