On iOS map WGS84, GCJ-02, BD-09 interchange Solution

Source: Internet
Author: User

On iOS map WGS84, GCJ-02, BD-09 interchange Solution

Recently developed projects involve the map location sharing module. Colleagues In the android group work first and use the Baidu map sdk. I am working later and use the mapkit of the iOS SDK, the problem is that the coordinates of the same longitude and latitude are greatly different on iOS and Android. Check the information of Apple map data source in the mainland is AMAP, check AMAP using GCJ-02, Baidu map sdk is BD-09, I had to write a class to switch between sending and receiving, which was a little painful. Someone on Github wrote a ready-made conversion class. For details, refer to the reference portal. For the main code, see:

Header file:

 

# Import
 
  
# Import
  
   
@ Interface JZLocationConverter: NSObject/*** @ brief world standard geographic coordinates (WGS-84) to the Chinese national test Bureau geographic coordinates (GCJ-02) <Mars coordinates> ** #### only the coordinates within the range of mainland China are valid, and the outside directly return the world standard coordinates ** @ param location the world standard geographic coordinates (WGS-84) ** @ return the geographic coordinates (GCJ-02) of the China National test Bureau <Mars coordinates> */+ (CLLocationCoordinate2D) wgs84ToGcj02 :( CLLocationCoordinate2D) location; /*** @ brief (GCJ-02, need to precisely locate the scene with caution ** @ param location China National test Bureau geographic coordinates (GCJ-02) ** @ return world standard geographic coordinates (WGS-84) */+ (CLLocationCoordinate2D) gcj02ToWgs84 :( CLLocationCoordinate2D) location;/*** @ brief world standard geographic coordinates (WGS-84) to Baidu geographic coordinates (BD-09) *** @ param location world standard geographic coordinates (WGS-84) ** @ return Baidu geographic coordinates (BD-09) */+ (CLLocationCoordinate2D) wgs84ToBd09 :( CLLocationCoordinate2D) location;/*** @ brief China National Geographic coordinates (GCJ-02) <Mars coordinates> converted to Baidu geographic coordinates (BD-09) ** @ param location China National test Bureau geographic coordinates (GCJ-02) <Mars coordinates> ** @ return Baidu geographic coordinates (BD-09) */+ (CLLocationCoordinate2D) gcj02ToBd09 :( CLLocationCoordinate2D) location;/*** @ brief Baidu geographic coordinates (BD-09) converted to the geographic coordinates (GCJ-02) <Mars coordinates> ** @ param location Baidu geographic coordinates (BD-09) ** @ return China National test Bureau geographic coordinates (GCJ-02) <Mars coordinates> */+ (CLLocationCoordinate2D) bd09ToGcj02 :( CLLocationCoordinate2D) location;/*** @ brief Baidu geographic coordinates (BD-09) converted to the world standard geographic coordinates (WGS-84) ** #### this interface has an error of about 1-2 meters, You need to precisely locate the scene with caution ** @ param location Baidu geographic coordinates (BD-09) ** @ return world standard geographic coordinates (WGS-84) */+ (CLLocationCoordinate2D) bd09ToWgs84 :( CLLocationCoordinate2D) location; @ end
  
 

Implementation File

 

 

#import JZLocationConverter.h#import 
 
  #define LAT_OFFSET_0(x,y) -100.0 + 2.0 * x + 3.0 * y + 0.2 * y * y + 0.1 * x * y + 0.2 * sqrt(fabs(x))#define LAT_OFFSET_1 (20.0 * sin(6.0 * x * M_PI) + 20.0 * sin(2.0 * x * M_PI)) * 2.0 / 3.0#define LAT_OFFSET_2 (20.0 * sin(y * M_PI) + 40.0 * sin(y / 3.0 * M_PI)) * 2.0 / 3.0#define LAT_OFFSET_3 (160.0 * sin(y / 12.0 * M_PI) + 320 * sin(y * M_PI / 30.0)) * 2.0 / 3.0#define LON_OFFSET_0(x,y) 300.0 + x + 2.0 * y + 0.1 * x * x + 0.1 * x * y + 0.1 * sqrt(fabs(x))#define LON_OFFSET_1 (20.0 * sin(6.0 * x * M_PI) + 20.0 * sin(2.0 * x * M_PI)) * 2.0 / 3.0#define LON_OFFSET_2 (20.0 * sin(x * M_PI) + 40.0 * sin(x / 3.0 * M_PI)) * 2.0 / 3.0#define LON_OFFSET_3 (150.0 * sin(x / 12.0 * M_PI) + 300.0 * sin(x / 30.0 * M_PI)) * 2.0 / 3.0#define RANGE_LON_MAX 137.8347#define RANGE_LON_MIN 72.004#define RANGE_LAT_MAX 55.8271#define RANGE_LAT_MIN 0.8293// jzA = 6378245.0, 1/f = 298.3// b = a * (1 - f)// ee = (a^2 - b^2) / a^2;#define jzA 6378245.0#define jzEE 0.00669342162296594323@implementation JZLocationConverter+ (double)transformLat:(double)x bdLon:(double)y{    double ret = LAT_OFFSET_0(x, y);    ret += LAT_OFFSET_1;    ret += LAT_OFFSET_2;    ret += LAT_OFFSET_3;    return ret;}+ (double)transformLon:(double)x bdLon:(double)y{    double ret = LON_OFFSET_0(x, y);    ret += LON_OFFSET_1;    ret += LON_OFFSET_2;    ret += LON_OFFSET_3;    return ret;}+ (BOOL)outOfChina:(double)lat bdLon:(double)lon{    if (lon < RANGE_LON_MIN || lon > RANGE_LON_MAX)        return true;    if (lat < RANGE_LAT_MIN || lat > RANGE_LAT_MAX)        return true;    return false;}+ (CLLocationCoordinate2D)gcj02Encrypt:(double)ggLat bdLon:(double)ggLon{    CLLocationCoordinate2D resPoint;    double mgLat;    double mgLon;    if ([self outOfChina:ggLat bdLon:ggLon]) {        resPoint.latitude = ggLat;        resPoint.longitude = ggLon;        return resPoint;    }    double dLat = [self transformLat:(ggLon - 105.0)bdLon:(ggLat - 35.0)];    double dLon = [self transformLon:(ggLon - 105.0) bdLon:(ggLat - 35.0)];    double radLat = ggLat / 180.0 * M_PI;    double magic = sin(radLat);    magic = 1 - jzEE * magic * magic;    double sqrtMagic = sqrt(magic);    dLat = (dLat * 180.0) / ((jzA * (1 - jzEE)) / (magic * sqrtMagic) * M_PI);    dLon = (dLon * 180.0) / (jzA / sqrtMagic * cos(radLat) * M_PI);    mgLat = ggLat + dLat;    mgLon = ggLon + dLon;        resPoint.latitude = mgLat;    resPoint.longitude = mgLon;    return resPoint;}+ (CLLocationCoordinate2D)gcj02Decrypt:(double)gjLat gjLon:(double)gjLon {    CLLocationCoordinate2D  gPt = [self gcj02Encrypt:gjLat bdLon:gjLon];    double dLon = gPt.longitude - gjLon;    double dLat = gPt.latitude - gjLat;    CLLocationCoordinate2D pt;    pt.latitude = gjLat - dLat;    pt.longitude = gjLon - dLon;    return pt;}+ (CLLocationCoordinate2D)bd09Decrypt:(double)bdLat bdLon:(double)bdLon{    CLLocationCoordinate2D gcjPt;    double x = bdLon - 0.0065, y = bdLat - 0.006;    double z = sqrt(x * x + y * y) - 0.00002 * sin(y * M_PI);    double theta = atan2(y, x) - 0.000003 * cos(x * M_PI);    gcjPt.longitude = z * cos(theta);    gcjPt.latitude = z * sin(theta);    return gcjPt;}+(CLLocationCoordinate2D)bd09Encrypt:(double)ggLat bdLon:(double)ggLon{    CLLocationCoordinate2D bdPt;    double x = ggLon, y = ggLat;    double z = sqrt(x * x + y * y) + 0.00002 * sin(y * M_PI);    double theta = atan2(y, x) + 0.000003 * cos(x * M_PI);    bdPt.longitude = z * cos(theta) + 0.0065;    bdPt.latitude = z * sin(theta) + 0.006;    return bdPt;}+ (CLLocationCoordinate2D)wgs84ToGcj02:(CLLocationCoordinate2D)location{    return [self gcj02Encrypt:location.latitude bdLon:location.longitude];}+ (CLLocationCoordinate2D)gcj02ToWgs84:(CLLocationCoordinate2D)location{    return [self gcj02Decrypt:location.latitude gjLon:location.longitude];}+ (CLLocationCoordinate2D)wgs84ToBd09:(CLLocationCoordinate2D)location{    CLLocationCoordinate2D gcj02Pt = [self gcj02Encrypt:location.latitude                                                  bdLon:location.longitude];    return [self bd09Encrypt:gcj02Pt.latitude bdLon:gcj02Pt.longitude] ;}+ (CLLocationCoordinate2D)gcj02ToBd09:(CLLocationCoordinate2D)location{    return  [self bd09Encrypt:location.latitude bdLon:location.longitude];}+ (CLLocationCoordinate2D)bd09ToGcj02:(CLLocationCoordinate2D)location{    return [self bd09Decrypt:location.latitude bdLon:location.longitude];}+ (CLLocationCoordinate2D)bd09ToWgs84:(CLLocationCoordinate2D)location{    CLLocationCoordinate2D gcj02 = [self bd09ToGcj02:location];    return [self gcj02Decrypt:gcj02.latitude gjLon:gcj02.longitude];}@end
 

Test cases:

 

 

Export gcj02 = longitude (114.21892734521, 29.575429778924); CLLocationCoordinate2D bd09 = [JZLocationConverter gcj02ToBd09: gcj02]; NSLog (@ % f, % f, bd09.latitude, bd09.long.pdf); // http://developer.baidu.com/map/index.php? Title = webapi/guide/changeposition // JZLocationConverter test data: 114.21892734521, 29.575429778924; Conversion Result: 114.224960, 29.581853 // Baidu api test data: 114.21892734521, 29.575429778924; Baidu api Conversion Result: 114.22539195429, 29.581585367458

In general, there is a slight deviation, but it is acceptable compared with the effect before processing.

 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.