iOS端如何解码Mapbox生成的encoded polyline编码折线?
解决方案
问题根因
MGLShape(data:encoding:) 方法仅支持传入标准GeoJSON格式的二进制数据,你传入的是Encoded Polyline编码字符串的二进制数据,格式不匹配因此返回nil。
实现方案
Mapbox的Encoded Polyline编码规则和通用的polyline编码规则完全一致,你可以通过以下两步实现需求:
1. 实现Encoded Polyline解码扩展
给String加扩展实现解码逻辑,直接输出坐标数组:
import CoreLocation import Mapbox extension String { func decodePolyline() -> [CLLocationCoordinate2D] { var coordinates = [CLLocationCoordinate2D]() var index = startIndex var lat = 0.0 var lon = 0.0 while index < endIndex { var byte = 0 var shift = 0 var result = 0 repeat { guard let asciiValue = self[index].asciiValue else { return coordinates } byte = Int(asciiValue) - 63 result |= (byte & 0x1F) << shift shift += 5 index = self.index(after: index) } while byte >= 0x20 let deltaLat = (result & 1) != 0 ? ~(result >> 1) : (result >> 1) lat += Double(deltaLat) shift = 0 result = 0 repeat { guard let asciiValue = self[index].asciiValue else { return coordinates } byte = Int(asciiValue) - 63 result |= (byte & 0x1F) << shift shift += 5 index = self.index(after: index) } while byte >= 0x20 let deltaLon = (result & 1) != 0 ? ~(result >> 1) : (result >> 1) lon += Double(deltaLon) coordinates.append(CLLocationCoordinate2D(latitude: lat / 1e5, longitude: lon / 1e5)) } return coordinates } }
2. 生成MGLShape实例
解码得到坐标数组后,直接生成MGLPolyline即可使用:
let encodedPolyline = "_nwfFteckVd@rIvEhEaB~Ht@lIxD~EvE~DfB|HdCeHrBwHnGT|ExDbGzAjGAyC{GjG[fGbA~@iICuIjG@lFqCrBpHj@lIaClHmGOiEbFVvIkCdHgEdFkGImGQoFbDgGgAmGl@iG_@}F_CmCgHZuI`@wIy@oIk@oI|BkH}EgE}BmH" let coordinates = encodedPolyline.decodePolyline() guard !coordinates.isEmpty else { // 解码失败逻辑处理 return } let polyline = MGLPolyline(coordinates: coordinates, count: UInt(coordinates.count)) let shapeSource = MGLShapeSource(identifier: "polyLineSource", shape: polyline, options: nil)
内容的提问来源于stack exchange,提问作者teradyl
相关产品推荐
相关产品推荐

