Drawing an AGSMutablePolyline through the 24-hour line

3452
9
10-25-2011 01:39 AM
GW
by
New Contributor
Hi there,

There does not seem to be any support for that. I see there is an option for the ArcGIS API for Flex (through normalization of the Central Meridian. What's out there for iOS?

Thanks !
0 Kudos
9 Replies
DiveshGoyal
Esri Regular Contributor
The AGSGeometryEngine class has a similar method.

For more information about wrap-around, refer to http://help.arcgis.com/en/arcgismobile/10.0/apis/iOS/2.0/concepts/index.html#/Enabling_Wrap_Around/0...
0 Kudos
GW
by
New Contributor
Hi,

Thanks for the tip. I have tried using that, and without examples it's pretty difficult to make sense out of it.

Is there any sample using that?

Thanks!
0 Kudos
GW
by
New Contributor
anyone for this question?
0 Kudos
GW
by
New Contributor
With this code:

    AGSPoint *aucklandmappoint =[[AGSPoint alloc] initWithX:aucklandMecPoint.x y:aucklandMecPoint.y spatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326]];       
    AGSPoint *losangelesmappoint =[[AGSPoint alloc] initWithX:losangelesMecPoint.x y:losangelesMecPoint.y spatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326] ];      
    [self.graphicsLayer removeAllGraphics]; 

    AGSMutablePolyline *polyline = [[AGSMutablePolyline alloc] initWithSpatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326]]; 

    [polyline addPathToPolyline]; 
    [polyline addPointToPath:losangelesmappoint];        
    [polyline addPointToPath:aucklandmappoint];        

    AGSGraphic *poly = [[AGSGraphic alloc] initWithGeometry:polyline symbol:[AGSSimpleLineSymbol simpleLineSymbolWithColor:[UIColor blackColor]] attributes:nil infoTemplateDelegate:nil];      
    [self.graphicsLayer addGraphic:poly]; 
    [poly release];  


I get:




When I use normalizeCentralMeridianOfGeometry on the polyline:
    AGSPoint *aucklandmappoint =[[AGSPoint alloc] initWithX:aucklandMecPoint.x y:aucklandMecPoint.y spatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326]];       
    AGSPoint *losangelesmappoint =[[AGSPoint alloc] initWithX:losangelesMecPoint.x y:losangelesMecPoint.y spatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326] ];      
    [self.graphicsLayer removeAllGraphics]; 

    AGSMutablePolyline *polyline = [[AGSMutablePolyline alloc] initWithSpatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326]]; 
    polyline = (AGSMutablePolyline *)[[AGSGeometryEngine defaultGeometryEngine]normalizeCentralMeridianOfGeometry:polyline];

    [polyline addPathToPolyline]; 
    [polyline addPointToPath:losangelesmappoint];        
    [polyline addPointToPath:aucklandmappoint];        

    AGSGraphic *poly = [[AGSGraphic alloc] initWithGeometry:polyline symbol:[AGSSimpleLineSymbol simpleLineSymbolWithColor:[UIColor blackColor]] attributes:nil infoTemplateDelegate:nil];    
    poly.geometry = [[AGSGeometryEngine defaultGeometryEngine]normalizeCentralMeridianOfGeometry:poly.geometry];    
    [self.graphicsLayer addGraphic:poly]; 
    [poly release];  


I get:



Note: wrap around is enabled
    self._mapView.wrapAround = YES;
0 Kudos
DiveshGoyal
Esri Regular Contributor
You have 2 calls to normalizeCentralMeridian, once when you instantiate a blank polyline, and the other after you have already assigned the polyline to a graphic. Both of these will have no affect. The first call does nothing because the polyline is empty. The second does infact normalize and return a new polyline, but your graphic is already set up with the original un-normalized polyline.

You need to call normalize after you add the last vertex to the polyline, and before you assign the polyline to the graphic.
0 Kudos
GW
by
New Contributor
Hi Divesh,

I am now using the following according to your instructions but cannot see a polyline across the dateline as expected:

    
AGSPoint *aucklandmappoint =[[AGSPoint alloc] initWithX:aucklandMecPoint.x y:aucklandMecPoint.y spatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326]];       
    AGSPoint *losangelesmappoint =[[AGSPoint alloc] initWithX:losangelesMecPoint.x y:losangelesMecPoint.y spatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326] ];  
    [self.graphicsLayer removeAllGraphics]; 

    AGSMutablePolyline *polyline = [[AGSMutablePolyline alloc] initWithSpatialReference:[AGSSpatialReference spatialReferenceWithWKID:4326]]; 
    [polyline addPathToPolyline]; 
    [polyline addPointToPath:losangelesmappoint];        
    [polyline addPointToPath:aucklandmappoint];        
    polyline = (AGSMutablePolyline *)[[AGSGeometryEngine defaultGeometryEngine]normalizeCentralMeridianOfGeometry:polyline];    
    AGSGraphic *poly = [[AGSGraphic alloc] initWithGeometry:polyline symbol:[AGSSimpleLineSymbol simpleLineSymbolWithColor:[UIColor blackColor]] attributes:nil infoTemplateDelegate:nil];    
    [self.graphicsLayer addGraphic:poly]; 
    [poly release]; 
0 Kudos
GW
by
New Contributor
Bump.

If this is a bug, where can I submit this?
0 Kudos
GW
by
New Contributor
Ok, I dug deeper in this.

It appeared that the map spatial reference I was using (based on the tiled layer) was not consistent with the graphics spatial reference.

 NSURL *mapUrl = [NSURL URLWithString:@"http://services.arcgisonline.com/ArcGIS/rest/services/World_Topo_Map/MapServer"];
 AGSTiledMapServiceLayer *tiledLyr = [AGSTiledMapServiceLayer tiledMapServiceLayerWithURL:mapUrl];


(the spatial reference for this URL being 102100)

is now paired with

    AGSMutablePolyline *polyline = [[AGSMutablePolyline alloc] initWithSpatialReference:[AGSSpatialReference spatialReferenceWithWKID:102100]]; 


Fixing this now always displays the polyline reglardless whether normalizeCentralMeridianOfGeometry is used or not. Now, even when using normalizeCentralMeridianOfGeometry, the polyline is always drawn so that it does not cross the dateline.



I have modified the SketchLayerSample application to demonstrate this issue. It's attached to this post.

One last thing is when trying to show the mapview's spatial reference, I alway get a null back. As opposed to graphics used in the app. The sample attached also shows that.
0 Kudos
NimeshJarecha
Esri Regular Contributor
You really need to understand few things about wrap around and normalizing geometries.

Wrap around:

There are two ways you can reach to Auckland from Los Angeles. One by crossing the date line (from [-118.2436849,34.0522342] to [-185.233,-36.8667]) and another without crossing the date line (from [-118.2436849,34.0522342] to [174.767,-36.8667]).

Without crossing the date line: You don't need the warp around since the geometry is not crossing the date line. See attached first image.
By crossing the date line: If wrap around is not enabled then see how geometry looks (see 2nd image) and see 3rd image, how geometry looks when warp around is enabled.

Normalizing Geometries:

What normalizeCentralMeridianOfGeometry does?

If the geometry is outside -180 and +180 then it cuts the geometry into parts and folds into -180 and +180. You do not need to USE this method if you are not intending to store these geometry in the geodatabase (either personal, file or see). If you just want to display them on the map then wrap around is enough.

For more information about wrap-around, refer to Wrap Around documentation.

I also added a switch to enable/disable wrap around so you can see the effect. See modifications I made in the your attached project.

One last thing is when trying to show the mapview's spatial reference, I alway get a null back.


This is because you are trying to check it too soon. You are adding the base layer in the viewDidLoad method and by the time you check the spatial reference of the mapView, the map is not loaded yet. You should check it in the mapViewDidLoad delegate method. See modifications in attached project.

One more thing, you are converting your WGS 1984 (4326) geometries into Web Mercator (102100) with your own function called lonLat2Mercator. The calculation seems to be incorrect. Please use the function AGSGeometryGeographicToWebMercator available in the SDK for the same. See code in attached project.

Hope, I made all points clear. Please let me know if you still have any question.

Regards,
Nimesh
0 Kudos