使用 Mapbox iOS SDK 构建条件表达式
Building a conditional expression using the Mapbox iOS SDK
我正在更新使用 Mapbox v6 SDK 的现有 iOS 应用程序。该应用程序使用点要素数组定义形状源,并指定应根据特定半径对点进行聚类。这是执行此操作的代码:
let source = MGLShapeSource(identifier: sourceIdentifier, features: features, options: [.clustered: true, .clusterRadius: 50.0, .maximumZoomLevelForClustering: 14.0])
我还定义了一个圆形样式图层来在地图上显示集群:
let circularClusterLayer = MGLCircleStyleLayer(identifier: "clusteredMarkers", source: source)
circularClusterLayer.predicate = NSPredicate(format: "cluster == YES")
这按预期工作,但现在我需要根据位于集群中的所有要素的属性定义圆圈颜色。具体来说,我的每个特征在其名为 .needsHelp
的属性字典中都有一个布尔值 属性。我正在尝试根据以下逻辑为聚类标记定义圆圈颜色:
if any of the features in the cluster have .needsHelp == true {
// set the circle color = UIColor.red
circularClusterLayer.circleColor = NSExpression(forConstantValue: UIColor.red)
} else {
// set the circle color = UIColor.gray
circularClusterLayer.circleColor = NSExpression(forConstantValue: UIColor.gray)
}
我很确定我应该能够构建一个表达式,如果集群中的任何特征具有 .needsHelp == true
则 returns 为真,否则 returns 为假。而且我相信这个表达式会像这样分配给源的 .clusterProperties 选项:
let expression1 = NSExpression(mglJSONObject: ["any", ["==", ["boolean", ["get", "isInEmergency"]], true]])
let expression2 = NSExpression(forConstantValue: UIColor.red)
let clusterPropertyDictionary: NSDictionary = ["clusterContainsFeatureThatNeedsHelp" : [expression1, expression2]]
let selectedContactsSource = MGLShapeSource(identifier: sourceIdentifier, features: features, options: [.clustered: true, .clusterRadius: 50.0, .maximumZoomLevelForClustering: 14.0, .clusterProperties: clusterPropertyDictionary])
我一直在查看 Mapbox expressions guide,我认为我应该使用“任何”决策表达式来返回一个布尔值,指示是否有任何特征具有 .needsHelp == true
.但到目前为止,我一直无法将类似 LISP 的表达式语法转换为有效的 NSExpression。
我假设除了上面的表达式之外,我还需要另一个表达式来检查“clusterContainsFeatureThatNeedsHelp”的值,然后相应地设置圆圈颜色。我最好的猜测是它看起来像这样:
// TODO: check value of clusterContainsFeatureThatNeedsHelp to determine circle color
circularClusterLayer.circleColor = NSExpression(forConditional: NSPredicate(format: "%K == %@", "clusterContainsFeatureThatNeedsHelp", NSNumber(value: true)), trueExpression: NSExpression(forConstantValue: UIColor.red), falseExpression: NSExpression(forConstantValue: UIColor.gray))
不幸的是,我没有成功构建这些 NSExpressions 中的任何一个。以前有人做过这样的事吗?如果是这样,我将不胜感激任何提示或建议!
我终于搞定了。我现在像这样创建 clusterPropertyDictionary:
let firstExpression = NSExpression(format: "max:({$featureAccumulated, clusterContainsFeatureThatNeedsHelp})")
let secondExpression = NSExpression(format: "CAST(needsHelp, 'NSNumber')")
let clusterPropertiesDictionary = ["clusterContainsFeatureThatNeedsHelp" : [firstExpression, secondExpression]]
实际设置圆圈颜色的表达式如下所示:
let expressionForClusterCircleColor = NSExpression(
forConditional: NSPredicate(format: "clusterContainsFeatureThatNeedsHelp > 0"),
trueExpression: NSExpression(forConstantValue: UIColor.red),
falseExpression: NSExpression(forConstantValue: UIColor.gray)
)
circularClusterLayer.circleColor = expressionForClusterCircleColor
我正在更新使用 Mapbox v6 SDK 的现有 iOS 应用程序。该应用程序使用点要素数组定义形状源,并指定应根据特定半径对点进行聚类。这是执行此操作的代码:
let source = MGLShapeSource(identifier: sourceIdentifier, features: features, options: [.clustered: true, .clusterRadius: 50.0, .maximumZoomLevelForClustering: 14.0])
我还定义了一个圆形样式图层来在地图上显示集群:
let circularClusterLayer = MGLCircleStyleLayer(identifier: "clusteredMarkers", source: source)
circularClusterLayer.predicate = NSPredicate(format: "cluster == YES")
这按预期工作,但现在我需要根据位于集群中的所有要素的属性定义圆圈颜色。具体来说,我的每个特征在其名为 .needsHelp
的属性字典中都有一个布尔值 属性。我正在尝试根据以下逻辑为聚类标记定义圆圈颜色:
if any of the features in the cluster have .needsHelp == true {
// set the circle color = UIColor.red
circularClusterLayer.circleColor = NSExpression(forConstantValue: UIColor.red)
} else {
// set the circle color = UIColor.gray
circularClusterLayer.circleColor = NSExpression(forConstantValue: UIColor.gray)
}
我很确定我应该能够构建一个表达式,如果集群中的任何特征具有 .needsHelp == true
则 returns 为真,否则 returns 为假。而且我相信这个表达式会像这样分配给源的 .clusterProperties 选项:
let expression1 = NSExpression(mglJSONObject: ["any", ["==", ["boolean", ["get", "isInEmergency"]], true]])
let expression2 = NSExpression(forConstantValue: UIColor.red)
let clusterPropertyDictionary: NSDictionary = ["clusterContainsFeatureThatNeedsHelp" : [expression1, expression2]]
let selectedContactsSource = MGLShapeSource(identifier: sourceIdentifier, features: features, options: [.clustered: true, .clusterRadius: 50.0, .maximumZoomLevelForClustering: 14.0, .clusterProperties: clusterPropertyDictionary])
我一直在查看 Mapbox expressions guide,我认为我应该使用“任何”决策表达式来返回一个布尔值,指示是否有任何特征具有 .needsHelp == true
.但到目前为止,我一直无法将类似 LISP 的表达式语法转换为有效的 NSExpression。
我假设除了上面的表达式之外,我还需要另一个表达式来检查“clusterContainsFeatureThatNeedsHelp”的值,然后相应地设置圆圈颜色。我最好的猜测是它看起来像这样:
// TODO: check value of clusterContainsFeatureThatNeedsHelp to determine circle color
circularClusterLayer.circleColor = NSExpression(forConditional: NSPredicate(format: "%K == %@", "clusterContainsFeatureThatNeedsHelp", NSNumber(value: true)), trueExpression: NSExpression(forConstantValue: UIColor.red), falseExpression: NSExpression(forConstantValue: UIColor.gray))
不幸的是,我没有成功构建这些 NSExpressions 中的任何一个。以前有人做过这样的事吗?如果是这样,我将不胜感激任何提示或建议!
我终于搞定了。我现在像这样创建 clusterPropertyDictionary:
let firstExpression = NSExpression(format: "max:({$featureAccumulated, clusterContainsFeatureThatNeedsHelp})")
let secondExpression = NSExpression(format: "CAST(needsHelp, 'NSNumber')")
let clusterPropertiesDictionary = ["clusterContainsFeatureThatNeedsHelp" : [firstExpression, secondExpression]]
实际设置圆圈颜色的表达式如下所示:
let expressionForClusterCircleColor = NSExpression(
forConditional: NSPredicate(format: "clusterContainsFeatureThatNeedsHelp > 0"),
trueExpression: NSExpression(forConstantValue: UIColor.red),
falseExpression: NSExpression(forConstantValue: UIColor.gray)
)
circularClusterLayer.circleColor = expressionForClusterCircleColor