Map SDK - iOS

Ola Map SDK offers a robust toolkit for seamlessly integrating both basic and advanced mapping features into your iOS applications. By utilizing the Maps SDK for iOS, you can incorporate maps powered by Ola's data directly into your app. The SDK takes care of displaying the map and responding to user interactions like clicks and drags. Additionally, you can enhance your maps by adding markers, polylines, ground overlays, and info windows, which provide extra information for specific locations and enable user interaction with the map.

Specifications

Before proceeding, ensure that you meet the following prerequisites:
  • Minimum iOS version: iOS 13.0
  • Xcode Version: 12 or later

Sample App

Please refer to theGithub Sample Appfor getting better clarity on same.

Set up

You have to iOS Map SDK import all the xcframeworks in your iOS project. Make sure you embed all the frameworks in General > Frameworks, Libraries and Embedded Content. Next, You need to add Location Permission Authorization in your Info.plist file,
<key>NSLocationWhenInUseUsageDescription</key>
    <string>App wants to access your location</string>
    <key>NSLocationAlwaysAndWhenInUseUsageDescription</key>
    <string>App wants to access your location</string>
Now, you are good to initialize the OlaMapService instance in your view controller.

Load the map using the service instance. Ideally this method should be called in viewdidLoad() method of viewcontroller

Features

  • Dynamic Maps
  • Camera and View
  • Polyline
  • Shape
  • Marker
  • Info Window
  • Map Events and Gesture
  • Traffic Polyline
  • Marker Clustering
Dynamic Map

To render a map, you need to initialise OlaMapService first and then call loadMap(_:)

private let olaMap = OlaMapService(
        auth: .apiKey(key: "<API-KEY-FROM-DASHBOARD>"), 
        tileURL: URL(string: "<TILE-URL-FROM-DASHBOARD>"), 
        projectId: "WORKSPACE-ID"
    )
    olaMap.loadMap(onView: self.view)
    olaMap.addCurrentLocationButton(self.view)
    olaMap.setCurrentLocationMarkerColor(UIColor.systemBlue)
    olaMap.setDebugLogs(true)
    olaMap.delegate = self
    olaMap.setMaxZoomLevel(16.0)
Parameter nameDescription
apikeyAPIKey from Ola Maps Dashboard
tileURLRefer Tiles API in API Reference
projectIdRefer Dashboard for Project Identifier
userIdCustom UserID which is identified by Organization
Map Camera

You can control the Map POV area and bounds area which you want to show.

// Set Camera With Single Coordinate
    olaMap.setCamera(at: OlaCoordinate(latitude: 12.93177, longitude: 77.616370000000003), zoomLevel: 16.0)
    // Set Camera With Array of Coordinates
    let polylineSetOlaToKormangla: [OlaCoordinate] = [
        OlaCoordinate(latitude: 12.93177, longitude: 77.616370000000003),
        OlaCoordinate(latitude: 12.93168, longitude: 77.616870000000006)
    ]
    olaMap.setMapCamera(polylineSetOlaToKormangla, UIEdgeInsets(top: 8, left: 8, bottom: 8, right: 8))
Events and Gestures

This will enable rotation selection capability on Map, you can rotate the map by using two fingers.

olaMap.setRotatingGesture(true)

Then, You will set of extra gesture delegate callback which comes with OlaMapServiceDelegate

func didTapOnMap(_ coordinate: OlaCoordinate) {
        //TODO: If You tap on tile
    }
    
    func didTapOnMap(feature: POIModel) {
        //TODO: If You tap on any POI
    }
    
    func didLongTapOnMap(_ coordinate: OlaCoordinate) {
        //TODO: If You long press on tile
    }
    
    func didChangeCamera() {
        print("Map Camera Change")
    }
    
    func mapSuccessfullyLoaded() {
        print("Map Loaded Successfully")
    }
    
    func mapSuccessfullyLoadedStyle() {
        print("Map Loaded Style")
    }
Info Window

You can draw a Info Window which is a tool tip kind of view on Map.

let toolTipId = "tool-tip"
    let infoWindow = InfoAnnotationView(identifier: toolTipId, model: InfoAnnotationDecorator(), text: "I'm at OlaCampus", isActive: true)
    self.olaMap.setAnnotationMarker(at: self.olaCampus, annotationView: infoWindow, identifier: toolTipId)

And, to delete Info Window you can use

olaMap.removeAnnotation(by:"Annotation-ID")
Map Region Bounds

You can control the Map Visible Bounds when you have array of coordinates.

self.olaMap.setMapCamera([coordinate1, coordinate2])
Marker
  • Create Annotation Marker
  • We have created CustomAnnotationView Type which is inherited from OlaAnnotation.

    let cabAnnotation = CustomAnnotationView(identifier: identifier, image: UIImage(named: "IMAGE_NAME"))
        cabAnnotation.bounds = CGRect(x: 0, y: 0, width: 40, height: 40)
        cabAnnotation.setRotate(Double(Int.random(in: 0...360))) // Set Bearing Angle for Cab
        olaMap.setAnnotationMarker(at: coordinate, annotationView: cabAnnotation, identifier: cabAnnotation.identifier)
  • Delete Annotation
  • You will need AnnotationId to delete any annotation from the map.

    olaMap.removeAnnotation(by:"Annotation-ID")
Polyline

You will need an array of OlaCoordinates to draw a solid polyline

  • Create Polyline
  • let polylineSetOlaToKormangla: [OlaCoordinate] = [
            OlaCoordinate(latitude: 12.93177, longitude: 77.616370000000003),
            OlaCoordinate(latitude: 12.93168, longitude: 77.616870000000006),
            OlaCoordinate(latitude: 12.931610000000001, longitude: 77.616900000000001),
            OlaCoordinate(latitude: 12.931000000000001, longitude: 77.616770000000002),
            OlaCoordinate(latitude: 12.93097, longitude: 77.616709999999997),
            OlaCoordinate(latitude: 12.931480000000001, longitude: 77.614249999999998),
            OlaCoordinate(latitude: 12.93075, longitude: 77.614389999999986),
            OlaCoordinate(latitude: 12.93022, longitude: 77.61472999999998),
            OlaCoordinate(latitude: 12.92999, longitude: 77.614869999999982),
            OlaCoordinate(latitude: 12.929869999999999, longitude: 77.614949999999979),
            OlaCoordinate(latitude: 12.92981, longitude: 77.615049999999982),
            OlaCoordinate(latitude: 12.92975, longitude: 77.615239999999985),
        ]
        
        self.olaMap.showPolyline(identifier: "polyline-id", .solid, self.polylineSetOlaToKormangla, .darkGray)
  • Delete Polyline
  • self.olaMap.deletePolyline("polyline-id")
Shape

We have a capability to draw a geometrical shape like Polygon or Circle.

  • Create Polygon
  • You need to call drawPolgon(_:) to draw Polygon Geometry

    let coordinates: [OlaCoordinate] = [
            OlaCoordinate(latitude: 12.9320745, longitude: 77.6137873),
            OlaCoordinate(latitude: 12.931336, longitude: 77.6141494),
            OlaCoordinate(latitude: 12.9308027, longitude: 77.6167565),
            OlaCoordinate(latitude: 12.9317333, longitude: 77.6170891),
            OlaCoordinate(latitude: 12.9322679, longitude: 77.6142218),
            OlaCoordinate(latitude: 12.9320745, longitude: 77.6137873),
         ]
         let strokeColor: UIColor = UIColor.black
         let strokeWidth: CGFloat = 2.5
         let zoneColor: UIColor = UIColor.systemGreen.withAlphaComponent(0.25)
         
         olaMap.drawPolygon(identifier: "polygon-id", coordinates, zoneColor: zoneColor, strokeColor: strokeColor, storkeWidth: strokeWidth)
         olaMap.setMapCamera(coordinates)
  • Remove Polygon
  • You need to use deletePolygon(_:) method

    self.olaMap.deletePolygon("polygon-id")

For Circle, you can use `drawCircle(_:)` method.

Traffic Polyline

Along with Solid Polyline, we have the capability to draw Segmented Polyline. This data you will get from Directions API. Check Platform Documentation.

let polylineEncodedString = "ss|mAcpvxM}@KE@EFKfAAB?DQlACRQ`B?FCTKt@CNOlAANE\?\HVJTNXy@\QF]NoA{CiByEi@sAEKCCO[Uc@q@mAVq@WCqBQwEg@_BKEAOAG@mCg@m@M"
    let trafficCongestions = "0,3,0|3,4,0|4,5,0|5,7,0|7,8,0|8,10,10|10,12,10|12,14,10|14,15,10|15,16,0|16,19,5|19,21,5|21,23,0|23,24,0|24,25,0|25,26,0|26,28,0|28,30,5|30,31,5|31,33,5|33,35,5|35,36,5|36,38,5|38,39,5|39,40,0|40,41,0|41,44,0|44,45,0|45,47,0|47,48,5|48,49,5|49,50,0|50,51,0|51,52,0|52,53,0|53,54,0|54,55,0|55,56,0|56,57,0"
    self.olaMap.showTrafficPolyline(encodedPolyline: polylineEncodedString, travelAdvisory: trafficCongestions) { polylineID in
        print("Segmented PolylineID: (polylineID)")
    }
Marker Clustering

We have a capability to cluster markers under a single labled marker. In simple words, if you've large marker rendered in a single area, then map will automatically cluster them in a single marker with a label on in.

let coordinates: [OlaCoordinate] = [
            OlaCoordinate(latitude: 12.9320745, longitude: 77.6137873),
            OlaCoordinate(latitude: 12.931336, longitude: 77.6141494),
            OlaCoordinate(latitude: 12.9308027, longitude: 77.6167565),
            OlaCoordinate(latitude: 12.9317333, longitude: 77.6170891),
            OlaCoordinate(latitude: 12.9322679, longitude: 77.6142218),
            OlaCoordinate(latitude: 12.9320749, longitude: 77.6137873),
        ]
        
    let clusterMarkers = coordinates.map { coordinate in
        return ClusterMarker(markerId: coordinate.description, image: UIImage(named: "car")!, coordinate: coordinate)
    }
    
    self.olaMap.drawClusterMarker(clusterMarkers, clusterDecorator: ClusterViewDecorator(backgroundColor: UIColor.lightGray, opacity: 0.5, radius: 50, cluserViewRadius: 10, borderWidth: 1, borderColor: UIColor.darkGray, fontSize: 16, fontColor: UIColor.red))
    
    self.olaMap.setCamera(at: self.olaCampus, zoomLevel: 20)
      
To customize the Cluster, we have a class called ClusterViewDecorator, where you can
  • backgroundColor: Background Color of Cluster View
  • opacity: Opacity of Cluster View
  • radius: Cluster's Zone Radius
  • cluserViewRadius: Radius of Cluster View
  • borderWidth: Border Width of Cluster View
  • borderColor: Border Width of Cluster View
  • fontSize: Text Size of Text Label on Cluster View
  • fontColor: Color of Text Label on Cluster View

And, to remove the Clusters from map, you need to just call a single method
  self.olaMap.clearCluster()