主题
arcade
字数统计: 5.2k 字
阅读时长: 约 16 分钟
当前版本: 4.29
AMD:
require(["geoscene/arcade"], (arcade) => { /* code goes here */ });
ESM:
import * as arcade from "@geoscene/core/arcade.js";
对象:
geoscene/arcade
起始版本:GeoScene Maps SDK for JavaScript 4.24
此模块允许您评估传统 GeoScene Arcade 配置文件之外的 Arcade 表达式。配置文件可定义有效输入变量 (即配置文件变量) 的表达式、支持的函数和表达式的有效返回类型。GeoScene Maps SDK for JavaScript 中执行的所有 Arcade 表达式必须符合编写它们的配置文件的规则。createArcadeExecutor 方法提供了一个 API,用于在预定义的 GeoScene Arcade 配置文件的上下文之外执行 Arcade 表达式。
此模块允许您执行以下操作:
在另一上下文中执行已为现有 GeoScene 配置文件编写的表达式。例如,最终用户可能为 WebMap 中的渲染器、弹出窗口或标签编写了表达式,并且表达式生成的数据应在 WebMap 外部的自定义组件、表或图表中显示。
定义自定义 Arcade 配置文件,并在应用程序中提供可配置的体验,以便用户编写自己的表达式。
开发人员可能希望利用 Arcade 提供的可链接功能集简化过滤和查询数据的过程。
另请参阅
方法概述
名称 | 返回值类值 | 描述 | 对象 |
---|---|---|---|
createArcadeExecutor() | Promise<ArcadeExecutor> | 将 Arcade 表达式及其配置文件编译为执行程序。 | arcade |
createArcadeProfile() | Profile | 为 GeoScene Maps SDK for JavaScript 中实现的 Arcade 配置文件创建配置文件定义。 | arcade |
方法详细说明
createArcadeExecutor
createArcadeExecutor(script, profile){Promise<ArcadeExecutor>}
将 Arcade 表达式及其配置文件编译为执行程序。执行程序可提供函数来评估配置文件变量的结果。
参数
scriptString
要编译和执行的 Arcade 表达式。
profileProfile
用于执行给定表达式的配置文件定义。配置文件定义了配置文件变量名称和数据类型,用户可以将其用作表达式中的输入。变量实例提供给执行程序函数。
返回
类型 | 描述 |
---|---|
Promise<ArcadeExecutor> | 解析为 ArcadeExecutor,它提供一个同步 (如果适用) 和异步函数,用于在提供有效的输入配置文件变量时计算编译的 Arcade 表达式。 |
示例
js
// Synchronous execution for all features in layer view
// % of the population not in labor force
const arcadeScript = "(($feature.POP_16UP - $feature.EMP_CY) / $feature.POP_16UP) \* 100"
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
const laborForceExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = laborForceExecutor.fieldsUsed;
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return laborForceExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
html
// Asynchronous execution for one feature clicked in the view
const profile = {
variables: [{
name: "$feature",
type: "feature"
}, {
name: "$layer",
type: "featureSet"
}]
};
// This expression executes on each feature click. It compares the % of the population
// not participating in the labor force with the same value of all features within
// one mile of the selected feature's location
const arcadeScript = `
var featureNotLaborForce = Round((($feature.POP_16UP - $feature.EMP_CY)/$feature.POP_16UP)\*100);
var id = $feature.OBJECTID;
var neighbors = Filter( Intersects( $layer, BufferGeodetic($feature, 1, "mile") ), "OBJECTID <> @id" );
if( Count(neighbors) == 0 ){
return "No neighbors within 1 mile";
}
var neighborsNotLaborForceAverage = Average(neighbors, "( (POP_16UP - EMP_CY) / POP_16UP) \* 100");
var difference = Round(featureNotLaborForce - neighborsNotLaborForceAverage);
var differenceText = IIF(difference > 0, "+"+difference, Text(difference));
return differenceText;
`;
const neighborhoodExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = neighborhoodExecutor.fieldsUsed;
view.on("click", async (event) => {
const hitResponse = await view.hitTest(event, include: { layer });
const hitGraphic = hitResponse?.results[0].graphic;
const scriptResult = await neighborhoodExecutor.executeAsync({
"$feature": hitGraphic,
"$layer": hitGraphic.layer
}, {
spatialReference: view.spatialReference
});
// display the value of scriptResult in a UI component or use it
// in some form of client-side analysis
});
createArcadeProfile
createArcadeProfile(profileName){Profile}
起始版本:GeoScene Maps SDK for JavaScript 4.25
为 GeoScene Maps SDK for JavaScript 中实现的 Arcade 配置文件创建配置文件定义。此操作的结果应提供给 createArcadeExecutor 方法。
参数
profileNameString
要创建的 Arcade 配置文件定义的名称。
可能值:"form-constraint"|"feature-z"|"field-calculation"|"form-calculation"|"labeling"|"popup"|"popup-element"|"feature-reduction-popup"|"feature-reduction-popup-element"|"visualization"
返回
类型 | 描述 |
---|---|
Profile | 返回用于使用 ArcadeExecutor 执行表达式的配置文件定义。 |
另请参阅
示例
js
const labelingProfile = arcade.createArcadeProfile("labeling");
// creates the following object to be provided to the createArcadeExecutor method.
// {
// variables: [{
// name: "$feature",
// type: "feature"
// }]
// }
const labelExecutor = await createArcadeExecutor("$feature.NAME + ' COUNTY'", labelingProfile);
类型定义
ArcadeExecutor
ArcadeExecutor
该执行程序提供一个同步 (如果适用) 和异步函数,用于使用声明的配置文件变量的输入来计算编译的 Arcade 表达式。它还提供有关编译结果的元数据。
属性
executeExecuteFunction
可调用的函数,用于评估一组配置文件变量的编译表达式。将返回评估结果。仅当 isAsync
为 false 时,此函数才可用。
executeAsyncExecuteFunctionAsync
计算编译表达式的异步函数。此函数可始终用于评估表达式,但如果 isAsync
为 true,则必须使用此函数。
fieldsUsedString[]
使用 $feature
配置变量或需要字段名的函数 (如 Expects
) 时,引用编译表达式中使用的字段名。此处引用的字段名应由底层图层或数据存储请求。在 JavaScript 中,这通常使用 layer.outFields
完成。
geometryUsedBoolean
指示表达式是访问还是使用要素的几何。
isAsyncBoolean
指示编译后的表达式是否使用 FeatureSet 函数访问数据,因此必须使用 executeAsync
函数执行。如果为 false
,则可以使用 execute
或 executeAsync
执行表达式。
另请参阅
示例
js
// Synchronous execution for all features in layer view
// % of the population not in labor force
const arcadeScript = "(($feature.POP_16UP - $feature.EMP_CY) / $feature.POP_16UP) \* 100"
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
const laborForceExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = laborForceExecutor.fieldsUsed;
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return laborForceExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
html
// Asynchronous execution for one feature clicked in the view
const profile = {
variables: [{
name: "$feature",
type: "feature"
}, {
name: "$layer",
type: "featureSet"
}]
};
// This expression executes on each feature click. It compares the % of the population
// not participating in the labor force with the same value of all features within
// one mile of the selected feature's location
const arcadeScript = `
var featureNotLaborForce = Round((($feature.POP_16UP - $feature.EMP_CY)/$feature.POP_16UP)\*100);
var id = $feature.OBJECTID;
var neighbors = Filter( Intersects( $layer, BufferGeodetic($feature, 1, "mile") ), "OBJECTID <> @id" );
if( Count(neighbors) == 0 ){
return "No neighbors within 1 mile";
}
var neighborsNotLaborForceAverage = Average(neighbors, "( (POP_16UP - EMP_CY) / POP_16UP) \* 100");
var difference = Round(featureNotLaborForce - neighborsNotLaborForceAverage);
var differenceText = IIF(difference > 0, "+"+difference, Text(difference));
return differenceText;
`;
const neighborhoodExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = neighborhoodExecutor.fieldsUsed;
view.on("click", async (event) => {
const hitResponse = await view.hitTest(event, include: { layer });
const hitGraphic = hitResponse?.results[0].graphic;
const scriptResult = await neighborhoodExecutor.executeAsync({
"$feature": hitGraphic,
"$layer": hitGraphic.layer
}, {
spatialReference: view.spatialReference
});
// display the value of scriptResult in a UI component or use it
// in some form of client-side analysis
});
js
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
// Arcade expression defined by user...
const syncExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = syncExecutor.fieldsUsed;
// throw error if expression from user uses
// invalid functions that require async execution
if(syncExecutor.isAsync){
throw new Error("Invalid expression. Expression should not use FeatureSet functions.");
}
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return syncExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
ArrayElementType
ArrayElementType
array
类型的配置文件变量的类型定义。
属性
typeString|String
变量的 Arcade 数据类型。请参阅 ProfileVariableInstanceType 以查看 Arcade 类型到 JavaScript 类型的映射。
可能值:"dictionary"|"feature"|"featureSet"|"featureSetCollection"|"geometry"|"number"|"text"|"date"|"dateOnly"|"time"|"boolean"|"knowledgeGraph"
propertiesProfileVariable[]
optional
仅在 type
为 dictionary
时适用。字典属性的类型定义。这些属性的名称不应以 $
字符开头。
elementTypeArrayElementType
optional
仅在 type
为 array
时适用。数组项目的类型定义。当用作输入配置文件变量时,Arcade 数组必须是单一类型。指示 elementType 时,不需要为元素指定名称。
ArrayVariable
ArrayVariable
Arcade 数组配置文件变量的类型定义。
属性
nameString
配置文件变量的名称。为遵循 Arcade 命名约定,这应以 $
字符开头,除非该变量嵌套在 DictionaryVariable 中。
typeString
变量的 Arcade 数据类型。对于 ArrayVariable,类型总是 array
。Arcade Array 对应的 JavaScript 类型是遵循 ProfileVariableInstanceType 中定义的规范的数组。
elementTypeArrayElementType
optional
数组项目的类型定义。当用作输入配置文件变量时,Arcade 数组必须是单一类型。指示 elementType 时,不需要为元素指定名称。
示例
js
const profile = {
variables: [{
name: "$checkpoints",
type: "array",
elementType: {
type: "feature"
}
}]
};
DictionaryVariable
DictionaryVariable
Arcade 字典配置变量的类型定义。
属性
nameString
配置文件变量的名称。为遵循 Arcade 命名约定,这应以 $
字符开头,除非该变量嵌套在另一个 DictionaryVariable 中。请参见下面的示例。
typeString
变量的 Arcade 数据类型。Arcade Dictionary 对应的 JavaScript 类型是遵循 ProfileVariableInstanceType 中定义的规范的纯对象。
值通常是 "dictionary"。
propertiesProfileVariable[]
optional
字典属性的类型定义。这些属性的名称不应以 $
字符开头。
示例
js
const profile = {
variables: [{
name: "$analysisParams",
type: "dictionary",
properties: [{
name: "distance",
type: "number"
}, {
name: "projectType",
type: "text"
}, {
name: "includeBuffer",
type: "boolean"
}]
}, {
name: "$projectLocation",
type: "feature"
}]
};
ExecuteContext
ExecuteContext
Arcade 表达式的执行上下文。
属性
spatialReferenceSpatialReference
optional
几何函数中输入几何的预期空间参考。如果在地图的上下文中执行表达式,则将视图的空间参考设置为此属性。如果在图层的上下文中执行表达式,则使用该图层的空间参考。如果未指定,则空间参考默认为 WebMercator。
timeZoneString
自 4.28 开始 定义创建和显示 Arcade 日期类型的默认时区。可能值包括在 View.timeZone 上设置的任何时区。通常,如果 Arcade 上下文的配置文件涉及地图或源自地图的要素,则应在此处设置 View.timeZone 值。默认情况下,时区设置为"system”。
默认值:system
示例
js
// the input feature's geometry is expected
// to be in the spatial reference of the view
// All Arcade dates will be represented in the
// time zone of the view or web map.
await executor.executeAsync({
"$feature": feature
}, {
spatialReference: view.spatialReference,
timeZone: view.timeZone
});
js
// the input feature's geometry is expected
// to be in the spatial reference of the layer
await executor.executeAsync({
"$feature": feature
}, {
spatialReference: layer.spatialReference
});
js
// the input feature's geometry is expected
// to be Web Mercator
await executor.executeAsync({
"$feature": feature
});
ExecuteFunction
ExecuteFunction(profileVariableInstances, context?){ResultType}
与给定的配置文件变量实例同步执行编译的 Arcade 表达式。如果表达式使用 FeatureSet 函数访问数据,则不能使用此函数。
参数
profileVariableInstancesObject
键/值对的对象,其中键是创建执行器时定义的 ProfileVariable 的名称。键值类型必须为 ProfileVariableInstanceType。
contextExecuteContext
optional
用于执行表达式的上下文。
返回
类型 | 描述 |
---|---|
ResultType | 返回计算表达式的值。 |
示例
js
// Synchronous execution for all features in layer view
// % of the population not in labor force
const arcadeScript = "(($feature.POP_16UP - $feature.EMP_CY) / $feature.POP_16UP) \* 100"
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
const laborForceExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = laborForceExecutor.fieldsUsed;
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return laborForceExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
js
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
// Arcade expression defined by user...
const syncExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = syncExecutor.fieldsUsed;
// throw error if expression from user uses invalid functions
if(syncExecutor.isAsync){
throw new Error("Invalid expression. Expression should not use FeatureSet functions.");
}
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return syncExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
ExecuteFunctionAsync
ExecuteFunctionAsync(profileVariableInstances, context?){Promise<ResultType>}
与给定的配置文件变量实例异步执行编译的 Arcade 表达式。
参数
profileVariableInstancesObject
键/值对的对象,其中键是创建执行程序时定义的 ProfileVariable 的名称,其值的类型必须为 ProfileVariableInstanceType。
contextExecuteContext
optional
用于执行表达式的上下文。
返回
类型 | 描述 |
---|---|
Promise<ResultType> | 解析为评估表达式的值。 |
示例
html
// Asynchronous execution for one feature clicked in the view
const profile = {
variables: [{
name: "$feature",
type: "feature"
}, {
name: "$layer",
type: "featureSet"
}]
};
// This expression executes on each feature click. It compares the % of the population
// not participating in the labor force with the same value of all features within
// one mile of the selected feature's location
const arcadeScript = `
var featureNotLaborForce = Round((($feature.POP_16UP - $feature.EMP_CY)/$feature.POP_16UP)\*100);
var id = $feature.OBJECTID;
var neighbors = Filter( Intersects( $layer, BufferGeodetic($feature, 1, "mile") ), "OBJECTID <> @id" );
if( Count(neighbors) == 0 ){
return "No neighbors within 1 mile";
}
var neighborsNotLaborForceAverage = Average(neighbors, "( (POP_16UP - EMP_CY) / POP_16UP) \* 100");
var difference = Round(featureNotLaborForce - neighborsNotLaborForceAverage);
var differenceText = IIF(difference > 0, "+"+difference, Text(difference));
return differenceText;
`;
const neighborhoodExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = neighborhoodExecutor.fieldsUsed;
view.on("click", async (event) => {
const hitResponse = await view.hitTest(event, include: { layer });
const hitGraphic = hitResponse?.results[0].graphic;
const scriptResult = await neighborhoodExecutor.executeAsync({
"$feature": hitGraphic,
"$layer": hitGraphic.layer
}, {
spatialReference: view.spatialReference
});
// display the value of scriptResult in a UI component or use it
// in some form of client-side analysis
});
Profile
Profile
定义配置文件输入变量的定义。这包括一个对象数组,用于指定每个配置文件变量的名称及其 Arcade 数据类型。所有配置文件名称必须以 $
字符开头。
属性
variablesProfileVariable[]
用作编译表达式输入的配置文件变量的 Arcade 类型定义。
示例
js
const profile = {
variables: [{
name: "$mapClick",
type: "geometry"
}, {
name: "$threshold",
type: "number"
}, {
name: "$feature",
type: "feature"
}, {
name: "$map",
type: "featureSetCollection"
}]
};
ProfileVariable
ProfileVariable SimpleVariable|DictionaryVariable|ArrayVariable
配置文件变量的类型定义。有关更多信息和示例,请参阅各个配置文件变量类型。
ProfileVariableInstanceType
ProfileVariableInstanceType Graphic|Geometry|FeatureSet|FeatureLayer|Map|KnowledgeGraph|String|Number|Boolean|Date|Object|Array
使用 ExecuteFunction 或 ExecuteFunctionAsync 评估编译表达式时,可以用作配置文件变量输入的 JavaScript 类型。请参阅下表,了解以下 JavaScript 类型的映射,这些类型可用于为相应的 Arcade 数据类型混合配置文件变量。
Arcade 类型 | JS 类型 | 注 |
---|---|---|
Number | Number | |
Text | String | |
Date | Date | 从 Arcade 表达式返回的日期不会保留 Arcade 日期值中包含的时区信息。由于本地 JS 日期对象不包含时区信息,因此它们将始终以执行表达式的客户端的本地时间或系统时间显示。要在 Arcade 返回的日期中保留时区信息,表达式作者应在表达式的返回语句中将日期转换为 Arcade 文本值。 |
DateOnly | String | |
Time | String | |
Boolean | Boolean | |
Dictionary | Object | 具有键/值对的对象,其中键由 DictionaryVariable 定义,其值必须是 ProfileVariableInstanceType 之一。 |
KnowledgeGraph | KnowledgeGraph | 该值通常来自 KnowledgeGraphLayer.knowledgeGraph。 |
Array | Array | Arcade 数组是不可变的,必须是单个 ProfileVariableInstanceType。 |
Geometry | Geometry | |
Feature | Graphic | |
FeatureSet | FeatureLayer | FeatureSet |
FeatureSetCollection | Map | String |
ResultType
ResultType Number|String|Date|Boolean|Graphic|Geometry|Object|ResultType[]
从 Arcade 表达式返回的结果的 JavaScript 类型。
SimpleVariable
SimpleVariable
简单 Arcade 配置文件变量的类型定义。
属性
nameString
配置文件变量的名称。为遵循 Arcade 命名约定,这应以 $
字符开头,除非该变量嵌套在 DictionaryVariable 中。
typeString
变量的 Arcade 数据类型。请参阅 ProfileVariableInstanceType 以查看 Arcade 类型到 JavaScript 类型的映射。
可能值:"feature"|"featureSet"|"featureSetCollection"|"geometry"|"number"|"text"|"date"|"dateOnly"|"time"|"boolean"|"knowledgeGraph"
示例
js
const profile = {
variables: [{
name: "$mapClick",
type: "geometry"
}, {
name: "$threshold",
type: "number"
}, {
name: "$feature",
type: "feature"
}, {
name: "$map",
type: "featureSetCollection"
}]
};