Sketch Layer
The Sketch layer makes it easy to create and modify geometries interactively. Users can annotate maps with sketches and contribute geographic content by drawing shapes such as areas, lines, and points. You don't have to write any code to implement the sketching behavior. All you need to do is wire up the Sketch layer so that it can track and respond to user interaction.
A Sketch layer complements a Feature layer nicley. Geometries drawn by a Sketch layer can be used to create new features or reshape existing features in a Feature layer. These features can then be persisted in a Geodatabase using an ArcGIS Server Feature Service.
Sketch workflow
This section describes the user interaction required to create or modify a sketch.
- When the Sketch layer is active, simply tap on the map to add a vertex to the sketch. If you are sketching a polygon, polyline, or a multipoint, you can tap repeatedly to add more vertices to the sketch. If you are sketching a point, tapping on the map again will simply move the existing vertex to the new location.
- To add a vertex after a specific vertex, first select the vertex by tapping on it, and then tap on the map where you want to add the new vertex.
- To insert a vertex between two vertices, first select the mid-point between the two vertices by tapping on it. Next, move the mid point by tapping on the map where you want to insert the new vertex. This will insert a new vertex at the location you tapped on.
- To move a vertex, first select the vertex by tapping on it. Next, tap and hold on the vertex for a moment or two. If you have enabled the showMagnifierOnTapAndHold property on the map view, a magnifier should appear. You can then drag your finger to the location where you want to move the vertex to. When you release your finger, the vertex will be moved to that location.
Sketch Symbology
A sketch is made up of many different visual elements. Each element is symbolized independently. For example :
| ![]() |
You can change the symbology of each of these elements by modifying some properties on the AGSSketchGraphicsLayer class. The mainSymbol property allows you to modify the Line and Fill symbols for the sketch. The vertexSymbol, selectedVertexSymbol, and midVertexSymbol properties allow you modify the symbol for vertices, selected vertex, and the mid point between vertices respectively.
Using a Sketch Layer
To use the sketch layer, you need to instantiate an object of the AGSSketchGraphicsLayer class, and add it to the map. If you know the type of geometry the user needs to sketch, you can pass in a geometry while instantiating the layer. Alternatively, you can instantiate the layer without a geometry as shown below and then assign the geometry later.
AGSSketchGraphicsLayer* sketchLyr = [[[AGSSketchGraphicsLayer alloc] initWithGeometry:nil]autorelease];
[self.mapView addMapLayer:sketchLyr withName:@"Sketch Layer"];
The type of geometry you assign to the layer dictates the type of shape a user will be allowed to sketch. The geometry can be one of the following types :
- AGSMutablePoint
- AGSMutableMultipoint
- AGSMutablePolyline
- AGSMutablePolygon
Note, a mutable geometry needs to be assigned to the layer because this geometry will be updated by the layer as the user sketches.
If the geometry assigned to the layer is empty, the initial sketch will be blank and the user will be able to create a new sketch from scratch. However, If the geometry is not empty, the initial sketch will represent the existing geometry and the user will be able to modify it.
//empty geometry for new sketch
AGSMutablePolygon* sketchPolygon = [[[AGSMutablePolygon alloc] initWithSpatialReference:self.mapView.spatialReference]autorelease];
sketchLyr.geometry = sketchPolygon;
//or, existing geometry for modifying sketch
AGSMutablePolygon* sketchPolygon = [polygon mutableCopy];
sketchLyr.geometry = sketchPolygon;
Adding the sketch layer to a map and assigning it a geometry is not enough to begin the sketch operation. You also need to set it as the map's touch delegate so that it can track and respond to user interaction.
self.mapView.touchDelegate = sketchLyr;
![Note Note](rsrc/note.png)
Only one object can serve as the map's touch delegate at a time. Setting the Sketch layer as the delegate will replace any previous object serving as the delegate. Hence, you should delay making the Sketch layer a touch delegate till the time you actually want the user to start sketching.
At this point, the user can start sketching on the map and the geometry will be modified as the user sketches. You can access the sketch geometry at anytime as follows :
AGSGeometry* sketch = sketchLyr.geometry;
To start another sketch, you do not need to create a new layer. Simply assign the existing layer a new geometry.
Once the sketch workflow is over, grab the sketch layer's geometry, clear the layer, and unset the layer as the map's touch delegate to prevent any further sketches. Be sure to restore the original touch delegate to enable other parts of the application that depend upon tracking map touch events.
![Note Note](rsrc/note.png)
After the user finishes the sketch, it is recommended that you simplify the sketch geometry using simplifyGeometry: method on AGSGeometryEngine. This will make the necessary corrections if the geometry intersects itself, or if a polygon geometry has rings in reverse orientation. If wrap-around is enabled on the map, you should also normalize the geometry using normalizeCentralMeridianOfGeometry: method on AGSGeometryEngine.
Undo and Redo changes
The Sketch layer provides the ability to undo and redo changes made to the sketch. The layer uses Apple's NSUndoManager class under the hood to maintain a history of sketch changes. Whenever a sketch is modified, either by by invoking methods on the sketch layer or by interacting with the map, the layer keeps track of the change. You can undo and redo these sequence of changes by invoking corresponding methods on the NSUndoManager as follows :
NSUndoManager* mgr = sketchLyr.undoManager;
//Undo a change
if([mgr canUndo]){
[mgr undo];
}
//Or, Redo a change
if([mgr canRedo]){
[mgr redo];
}
For more information about Undo and Redo, refer to Apple's Undo Architecture guide
![Note Note](rsrc/note.png)
Sketch changes are specific to a geometry. The history of sketch changes is automatically cleared whenever the sketch layer's geometry is replaced.
Modifying a sketch programmatically
A sketch can be modified programmatically in addition to being modified interactively as described in the Sketch Workflowsection. This may be useful if you want to simplify the sketching process for the user or implement some advanced behavior such as sketching based on device's GPS coordinates as the device travels.
You can modify the sketch geometry programmatically through methods on the AGSSketchGraphicsLayer class such as insertVertex:inPart:atIndex:, moveVertexInPart:atIndex:toPoint:, removeVertexInPart:atIndex:, and so on. These methods allow you to make incremental changes to the geometry. You can also use applyGeometry: to completely reshape the existing sketch geometry. You can use this approach when you want to make bulk changes to the geometry, or if you want to use complex criteria for constructing geometries. For example, creating geodetically correct geometries.
The sketch layer will keep track of any changes made using these methods so that you can undo or redo them using the NSUndoManager.
![Note Note](rsrc/note.png)
You should avoid directly modifying the geometry object used by the sketch layer. This may cause the sketch display to get out of sync with the geometry. Furthermore, changes made to the geometry in this manner are not tracked by the undo manager.
Notifications
The sketch layer posts a Geometry Changed notification whenever its geometry is changed. You can subscribe to this notification as follows if you are interested in monitoring changes to the geometry :
//register self for receiving notifications
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(respondToGeomChanged:) name:@"GeometryChanged" object:nil];
//method to be called when notification is posted
- (void)respondToGeomChanged: (NSNotification*) notification {
//do something
}