在屏幕上绘制相对于彼此的GPS坐标,而不是*不*任何地图

时间:2011-09-28 15:33:16

标签: android gps

假设我在位置M(纬度,经度),我有3个GPS坐标A(lat,lon),B(lat,lon)和C(lat,lon),它们在500米的范围内在M周围的半径。

注意:我想在屏幕上相对于彼此绘制它们,但 到任何其他地图或其他任何地方,以及数字M周围的gps点可能会增加或减少,但总是在M周围500米处。

M将位于屏幕的中心。 ScreeWidth = 320,ScreenHeight = 400

我有以下信息

M =  31.484083, 74.392708,

A =  31.483552, 74.392386 and distance from M is 66.42 Meters approximately
B =  31.483534, 74.392532 and distance from M is 63.23 Meters approximately
C =  31.483421, 74.392434 and distance from M is 78.00 Meters approximately

M将在屏幕的WIDTH / 2和HEIGHT / 2处绘制

对于A,B和C,需要一个转换函数,它将以像素为单位返回x和y,其中RESPECT为M和

屏幕宽度和高度,请记住这些点总是在M周围500米范围内。

这样我就可以绘制这些点,如下图所示。

这是图片:

image https://picasaweb.google.com/lh/photo/J7PE6RuSqu7Pv9xv9D2PgQ?feat=directlink

我只需要x和y的转换功能,我知道如何在屏幕上绘制它们

2 个答案:

答案 0 :(得分:2)

嗯,你需要实现一个方法,将lat / lon映射到像素,将像素映射到lat lon ......或者确定距参考点M的距离/方位角的方法,然后将该距离/ azomith映射到a像素值。

如果您希望通过lat / lon引用 - 使用每像素纬度和每像素经度度数的某些设定度数的线性像素图。我建议去谷歌地球,并检查你感兴趣的区域的纬度和经度的不同是500米。纬度在世界各地的每个点都设定为60海里/度,而且我非常确定经度类似于每度60 * cos(纬度)海里(近似值,google this)。

如果您希望通过距离参考,我建议使用球形地球近似并使用半身构建方法来确定大球体的距离。如果您使用matlab,最好在文件交换中找到google或mathworks.com的例子。

有一种方法可以将lat lon或dist / az映射到pix值。其余的只是绘图。

祝你好运

下面是名为vreckon和geodistance的代码,你可以自己解析它,如果你想在java中实现 - 我已经自己做了vreckon所以我会给你工作的vreckon java,如果你想做地理距离(检查距离)在两个纬度点之间)你需要自己做。

VRECKON的JAVA代码::::::

hvDistance是距你的纬度点的水平距离,latitudeOrigin和longitudeOrigin是你的lat / lon位置,方位角是你的原点的方向。

输出将是新的纬度和经度点。如果你想在java中实现,你应该能够通过matlab代码并使用geodistance执行相同的操作。这是让您达到WGS84标准精度的确切内容。享受

private void vreckon(){
    double rng = hvDistance; 

    double m = 6;
    double a = 6378137.0;
    double f = 1/298.257223563;
    double b = a*(1-f);
    double lat0 = deg2rad(latitudeOrigin);
    double lon0 = deg2rad(longitudeOrigin);
    double az = deg2rad(azimuth);

    double axa = a*a;
    double bxb = b*b;

    double tan_U1 = (1-f)*Math.sin(lat0)/Math.cos(lat0);

    double U1 = Math.atan(tan_U1);
    double cos_alfa1 = Math.cos(az);
    double sig1 = Math.atan2(tan_U1, cos_alfa1);

    double cos_U1 = Math.cos(U1);
    double sin_alfa1 = Math.sin(az);

    double sin_alfa = cos_U1*sin_alfa1;

    double cos2_alfa = (1-sin_alfa)*(1+sin_alfa);
    double uxu = cos2_alfa*(axa-bxb)/bxb;

    double A = 1+uxu/16384*(4096+uxu*(-768+uxu*(320-175*uxu)));
    double B = uxu/1024*(256+uxu*(-128+uxu*(74-47*uxu)));

    double sig = rng/(b*A);

    double change = 1;

    double twosig_m;
    double cos_twosig_m;
    double cos2_twosig_m;
    double dsig;
    double sigold;

    while(Math.abs(change) > 1e-9){
        twosig_m = 2*sig1+sig;
        cos_twosig_m = Math.cos(twosig_m);
        cos2_twosig_m = cos_twosig_m*cos_twosig_m;
        dsig = B*Math.sin(sig)*(cos_twosig_m+1/4*B*(Math.cos(sig)*(-1+2.*cos2_twosig_m)-1/6*B*cos_twosig_m*(-3+4*(Math.sin(sig)*Math.sin(sig)))*(-3+4*cos2_twosig_m)));
        sigold = sig;
        sig = rng/(b*A)+dsig;
        change = sig-sigold;
    }

    twosig_m = 2*sig1+sig;

    cos_twosig_m = Math.cos(twosig_m);
    cos2_twosig_m = cos_twosig_m*cos_twosig_m;
    double sin_U1 = Math.sin(U1);

    double cos_sig = Math.cos(sig);
    double sin_sig = Math.sin(sig);
    double sin2_alfa = sin_alfa*sin_alfa;

    double latOut = Math.atan2(sin_U1*cos_sig+cos_U1*sin_sig*cos_alfa1,(1-f)*Math.sqrt(sin2_alfa+(sin_U1*sin_sig-cos_U1*cos_sig*cos_alfa1)*(sin_U1*sin_sig-cos_U1*cos_sig*cos_alfa1)));

    double lambda = Math.atan2(sin_sig*sin_alfa1,cos_U1*cos_sig-sin_U1*sin_sig*cos_alfa1);
    double C = f/16*cos2_alfa*(4+f*(4-3*cos2_alfa));
    double L = lambda-(1-C)*f*sin_alfa*(sig+C*sin_sig*(cos_twosig_m+C*cos_sig*(-1+2*cos2_twosig_m)));

    double lonOut = L+lon0;

    latOut = rad2deg(latOut);
    lonOut = rad2deg(lonOut);

    reckonedLatitude = latOut;
    reckonedLongitude = lonOut;
}

GEODISTANCE的MATLAB代码:::::

function [r az] = geodistance(lat1,lon1,lat2,lon2,ellip,earthR)
%GEODISTANCE: Calculates the distance in meters between two points on earth surface.
%
% Usage:  r = geodistance(lat1,lon1,lat2,lon2, ellipsoid ) ;
%
%     Coordinates values should be specified in decimal degrees.
%     Method can be an integer between 1 and 23, default is m = 6.
%         Methods 1 and 2 are based on spherical trigonometry and a
%         spheroidal model for the earth, respectively.
%     Methods 3 to 24 use Vincenty's formulae, based on ellipsoid
%         parameters.
%         Here it follows the correspondence between m and thge type of
%         ellipsoid:
%
%         m =  3 -> ANS ,        m =  4 -> GRS80,    m = 5 -> WGS72,
%         m =  6 -> WGS84,       m =  7 -> NSWC-9Z2,
%         m =  8 -> Clarke 1866, m =  9 -> Clarke 1880,
%         m = 10 -> Airy 1830,
%         m = 11 -> Bessel 1841 (Ethiopia,Indonesia,Japan,Korea),
%         m = 12 -> Bessel 1841 (Namibia),
%         m = 13 -> Sabah and Sarawak (Everest,Brunei,E.Malaysia),
%         m = 14 -> India 1830, m = 15 -> India 1956,
%         m = 16 -> W. Malaysia and Singapore 1948,
%         m = 17 -> W. Malaysia 1969,
%         m = 18 -> Helmert 1906, m = 19 -> Helmert 1960,
%         m = 20 -> Hayford International 1924,
%         m = 21 -> Hough 1960, m = 22 -> Krassovsky 1940,
%         m = 23 -> Modified Fischer 1960,
%         m = 24 -> South American 1969.
%
%     Important notes:
%
%    1)South latitudes are negative.
%    2)East longitudes are positive.
%    3)Great circle distance is the shortest distance between two points
%          on a sphere. This coincides with the circumference of a circle which
%          passes through both points and the centre of the sphere.
%    4)Geodesic distance is the shortest distance between two points on a spheroid.
%    5)Normal section distance is formed by a plane on a spheroid containing a
%          point at one end of the line and the normal of the point at the other end.
%          For all practical purposes, the difference between a normal section and a
%          geodesic distance is insignificant.
%    6)The method m=2 assumes a spheroidal model for the earth with an average
%          radius of 6364.963 km. It has been derived for use within Australia.
%          The formula is estimated to have an accuracy of about 200 metres over 50 km,
%          but may deteriorate with longer distances.
%          However, it is not symmetric when the points are exchanged.
%***************************************************************************************
% Based loosely from code from orodrig@aulg.pt
% Vastly modified and improved.
% By J. Sullivan 12/2010
%***************************************************************************************

%% Defensive Programming

error(nargchk(4,6,nargin));

if any([isempty(lat1) isempty(lon1) isempty(lat2) isempty(lon2)]);
    error('One or more input arguments are empty.')
end
%% Farm out to GPU, if possible
if any([numel(lat1) numel(lat2) numel(lon1) numel(lon2)] >  250000) ...
        && ~any([numel(lat1) numel(lat2) numel(lon1) numel(lon2)] > 6000000)
    [lat1 lat2 lon1 lon2] = makeIntoGPUArrays(lat1,lat2,lon1,lon2);
end
%% Prepare the Data
r = [ ];
lambda1 = lon1*pi/180;
phi1 = lat1*pi/180;
lambda2 = lon2*pi/180;
phi2 = lat2*pi/180;
isEast = lon1 < lon2;
L = lambda2 - lambda1;
%% Load Earth Ellipsoid Models
alla = [earthRadius 0 6378160 6378137.0 6378135 6378137.0 6378145 6378206.4 6378249.145,...
    6377563.396 6377397.155 6377483.865,...
    6377298.556 6377276.345 6377301.243 6377304.063 6377295.664 6378200 6378270 6378388  6378270 6378245,...
    6378155 6378160];

allf = [0 0  1/298.25 1/298.257222101 1/298.26 1/298.257223563 1/298.25 1/294.9786982 1/293.465,...
    1/299.3249646 1/299.1528128,...
    1/299.1528128 1/300.8017 1/300.8017 1/300.8017 1/300.8017 1/300.8017 1/298.3 1/297 1/297 1/297,...
    1/298.3 1/298.3 1/298.25];
%% Choose Ellipsoid
if nargin > 4 && length(ellip) == 2;
    m = inf;
    a = ellip(1);
    b = a*cos(ellip(2));
    f = (a-b)/a;
elseif nargin < 5
    m = 6;
    a = alla(6);
    f = allf(6);
    b = a*(1-f);
elseif length(ellip) == 1
    m = ellip;
    a = alla(ellip);
    f = allf(ellip);
    b = a*(1-f);
end
samePoint = gather(abs( lambda1 - lambda2 ) < eps) & gather(abs( phi1 - phi2 ) < eps);
%% Sheperical Earth
if m == 1 % Great Circle Distance, based on spherical trigonometry
    clear lat1 lat2 lon1 lon2
    if nargin < 6; earthR = a; end
    tmp = sin(phi1).*sin(phi2)+cos(phi1).*cos(phi2).*cos(lambda2-lambda1);
    tmp(tmp > 1) = 1;
    r = earthR.*acos(tmp);
    r = gather(abs(r));
    if nargout > 1
        az = atan2(cos(phi2).*sin(lambda2-lambda1),cos(phi1).*sin(phi2)...
            -sin(phi1).*cos(phi2).*cos(lambda2-lambda1));
        % Azimuths are undefined at the poles, so we choose a convention: zero at
        % the north pole and pi at the south pole.
        az(phi1 <= -pi/2) = 0;
        az(phi2 >=  pi/2) = 0;
        az(phi2 <= -pi/2) = pi;
        az(phi1 >=  pi/2) = pi;
        az = gather(rad2deg(az));
    end

elseif m == 2 % Spheroidal model for the earth
    % Azimuth Calculations for this model are NOT consistant with a
    % spheriod.

    term1 = 111.08956*( lat1 - lat2 + 0.000001 );
    term2 = cos( phi1  + ( (phi2 - phi1)/2 ) );
    term3 = ( lon2 - lon1 + 0.000001 )/( lat2 - lat1 + 0.000001 );
    r = 1000*abs( term1/cos( atan( term2*term3 ) ) );
    if nargout > 1
        az = atan2(cos(phi2).*sin(lambda2-lambda1),cos(phi1).*sin(phi2)...
            -sin(phi1).*cos(phi2).*cos(lambda2-lambda1));
        % Azimuths are undefined at the poles, so we choose a convention: zero at
        % the north pole and pi at the south pole.
        az(phi1 <= -pi/2) = 0;
        az(phi2 >=  pi/2) = 0;
        az(phi2 <= -pi/2) = pi;
        az(phi1 >=  pi/2) = pi;
        az = rad2deg(az);
    end

else
    %% Apply Vincenty's formulae
    clear lambda1 lambda2 lat1 lat2 lon1 lon2

    axa = a^2;
    bxb = b^2;

    U1 = atan( ( 1 - f )*tan( phi1 ) );
    U2 = atan( ( 1 - f )*tan( phi2 ) );

    clear phi1 phi2

    lambda     =  L;
    lambda_old = sqrt(-1);
    ntrials = 0;

    while gather(any(any( abs( lambda - lambda_old ) > 1e-9 )))

        ntrials = ntrials + 1;

        lambda_old = lambda;
        sin_sigma = sqrt( ( cos(U2).*sin(lambda) ).^2 + ( cos(U1).*sin(U2) - sin(U1).*cos(U2).*cos(lambda) ).^2 );
        cos_sigma = sin( U1 ).*sin( U2 ) + cos( U1 ).*cos( U2 ).*cos( lambda );
        sigma = atan2( sin_sigma,cos_sigma );
        sin_alpha = cos( U1 ).*cos( U2 ).*sin( lambda )./sin_sigma;
        cos2_alpha = 1 - sin_alpha.^2;
        cos_2sigmam = cos_sigma - 2.*sin( U1 ).*sin( U2 )./cos2_alpha;

        C = (f/16).*cos2_alpha.*( 4 + f.*( 4 - 3.*cos2_alpha ) );

        lambda  = L + ( 1 - C ).*f.*sin_alpha.*( sigma + C.*sin_sigma.*( ...
            cos_2sigmam + C.*cos_sigma.*( -1 + 2*( cos_2sigmam ).^2 ) ) );

        if ntrials > 1000
            disp('Convergence failure...')
            return
        end
    end
    clear C sin_alpha lambda_old L
    %% Get Distance After Convergence acheived
    uxu = cos2_alpha.*(axa - bxb)./bxb;
    clear cos2_alpha bxb axa
    A = 1 + (uxu/16384).*(4096 + uxu.*(-768 + uxu.*(320 - 175.*uxu)));
    B = (uxu./1024).*(256 + uxu.*(-128 + uxu.*(74 - 47.*uxu)));
    clear uxu
    delta_sigma = B.*sin_sigma.*(cos_2sigmam + (B/4).*(cos_sigma.*...
        (-1 + 2.*cos_2sigmam.^2) -(B/6).*cos_2sigmam.*(-3 + 4.*sin_sigma.^2)...
        .*(-3 + 4.*cos_2sigmam.^2)));
    clear sin_sigma cos_sigma cos_2sigmam B
    delta_sigma(isnan(delta_sigma)) = 0;
    r = gather(b.*A.*(sigma - delta_sigma));
    clear sigma A delta_sigma
    %% Same Point Check
    r(samePoint) = 0;
    %% Calculate Azimuth if needed
    if nargout >= 2
        lambda(gather(isnan(lambda)) & gather(isEast)) = pi/2;
        lambda(gather(isnan(lambda)) & ~gather(isEast)) = -pi/2;
        az = rad2deg(atan2(cos(U2).*sin(lambda),cos(U1).*sin(U2)-sin(U1).*cos(U2).*cos(lambda)));
        clear U1 U2 lambda
        az = gather(zero22pi(az));
        az(samePoint) = 0;
    end
end

% clearvars -except az r

答案 1 :(得分:2)

好吧最后我设法编写了一个转换函数,它可以帮助我并且工作正常,因为我在不同的位置进行了测试,并且参考了中心点(M)所有其他点都以完美的比例显示。

public static POINT XY(double centerLatitude, double centerLongitude, double Latitude, double Longitude, double MetersPerPixel) {
    double rto = 1/MetersPerPixel;
    double dLAT = ((centerLatitude - Latitude)/ 0.00001) * rto;
    double dLNG = -1 * ((centerLongitude - Longitude) / 0.00001) * rto;
    int y = (int)Math.round(dLAT);
    int x = (int)Math.round(dLNG);
    POINT crd = new POINT(x, y );
    return crd;
}