0
votes

MGLPolygonFeature is supposed to support MGLFeature as a series of attributes on the PolygonFeature.

However, I can find no documentation on how to go about setting attribute features at a polygon level. Most documentation refers to tile layer, or I am just missing the glue piece I need to solve this issue.

My goal is to assign a fill, opacity, stroke colour, and stroke width to a polygon at the time I create the polygon feature, so that when I create a multitude of polygons, they all have independent fill colours based on some criteria specific to that particular polygon.

Some attempted code to solve the issue is provided below - but as can be seen, something is missing in order to set the attributes.

    let polygon = MGLPolygonFeature(coordinates: coordinates, count: UInt(coordinates.count))
    let identifier = "\(name)"
    let source = MGLShapeSource(identifier: identifier, shape: polygon)
    let fill = MGLFillStyleLayer(identifier: identifier, source: source)
    fill.fillColor = NSExpression(forConstantValue: UIColor.green)
    fill.fillOpacity = NSExpression(forConstantValue: 0.3)
    polygon.attribute(forKey: "fillColor") = fill // non-mutable property cannot be added
    return polygon

The polygon itself does not have layer properties, but the documentation from mapbox seems to suggest that adding attributes is the way to achieve what I want.

Any clues to what I am missing?

1

1 Answers

0
votes

I used the following methods to solve the addition of colors to polygons.

func createSourceAndLayer(identifier: String, shapes: [MGLShape]) -> (MGLSource, MGLStyleLayer) {
    let source = MGLShapeSource(identifier: identifier, shapes: shapes)
    let layer = MGLLineStyleLayer(identifier: identifier, source: source)
    layer.lineColor = NSExpression(forConstantValue: UIColor.white)
    layer.lineWidth = NSExpression(forConstantValue: 2)
    
    return (source, layer)
}

func createFillLayer(identifier: String, source: MGLSource) -> MGLStyleLayer {
    let fillLayer = MGLFillStyleLayer(identifier: identifier, source: source)
    fillLayer.fillColor = NSExpression(forConstantValue: UIColor.red)
    fillLayer.fillOpacity = NSExpression(forConstantValue: 0.25)
    return fillLayer
}

Called and configured similar to the below.

    let (source, layer) = createSourceAndLayer(identifier: "sourceId", shapes: polygons)
    let fillLayer = createFillLayer(identifier: "fillId", source: source)
    style.addSource(source)

    // Layer is inserted at position count-1 which works for now but we don't really
    // control the z-index of the annotations (cows)
    style.insertLayer(layer, at: UInt(style.layers.count - 1))
    style.insertLayer(fillLayer, at: UInt(style.layers.count - 2))