After you've completed the Getting Started, take a look at the tutorials listed below. These tutorials demonstrate how the MXML and ActionScript code is used to perform various functions in the ArcGIS API for Flex. Understanding each element of the code and its syntax will increase your productivity and save time.
All tutorials contain an overview and how-to guide.
Using Map |
This tutorial shows you how to create an application with a map zoomed in to a specific location, illustrating how the ArcGIS API for Flex is used in an MXML page.
The following is the sample MXML code in its entirety:
<?xml version="1.0" encoding="utf-8"?> <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" xmlns:esri="http://www.esri.com/2008/ags" pageTitle="Tutorial - adding a map" > <esri:Map> <esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer" /> <esri:extent> <esri:Extent xmin="-17.3" ymin="-34.6" xmax="51.1" ymax="38.2"/> </esri:extent> </esri:Map> </mx:Application>
View a sample.
Your code should always contain the same two parts:
<esri:Map>
When you first use the esri namespace, Flex Builder automatically adds the namespace to the application tag. When you add <esri:Map>, Flex Builder automatically creates its matching end tag </esri:Map>.
<esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer" />
The StreetMap service, a tiled MapService layer, is initialized using the ArcGISTiledMapServiceLayer constructor. The URL is the endpoint for this service. This endpoint is a reference to a service that you can find out using Services Directory.
<esri:extent> <esri:Extent xmin="-17.3" ymin="-34.6" xmax="51.1" ymax="38.2"/> </esri:extent>
Using Query |
NOTE: The following discussion assumes that you are familiar with the basic concepts of Flex.
In this tutorial, you will learn how to use a query task to query information from an ArcGIS Server service. You will use Query, QueryTask, and FeatureSet to query a layer in a map and display the results. There are usually four steps involved in a query process:
The example below is a QueryTask where the user types in the name of a city. Based on this input, all cities that match the name are displayed on the map. Please refer to the end of this section for completed code.
The Map and its layers are used to provide a context to displaying the query results. The GraphicsLayer is used to symbolize and display the geometries of the query results. The code snippet below shows a map with an ArcGIS Server tiled map service layer and a graphics layer added to the map. The features that are rendered by the graphics layer will use the symbol defined by "infoSymbol1", that will be explained later.
<esri:Map id="map"> <esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_Imagery_World_2D/MapServer"/> <esri:GraphicsLayer id="myGraphicsLayer" symbol="{infoSymbol1}"/> </esri:Map>
It is not always necessary to have a map to perform a query. In situations where you just want to populate a DataGrid with the query results, a map is not needed (see sample).
The QueryTask sets up the URL of the layer that the query will work with. Note the URL includes the layer ID. In the code example below the layer ID is 0.
<esri:QueryTask id="queryTask" url="http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/Specialty/ESRI_StatesCitiesRivers_USA/MapServer/0" />
The Query defines the criteria that will be used for executing the query. The actual filter is set by the "text" attribute (shorthand for a WHERE clause using LIKE operator) that is bound to the value of a text input component that we will see later. The field used is the display field defined in the map document. You can determine the display field for a layer in Services Directory. Since we want to display the results of our query we set the attribute "returnGeometry" to true.
In this example, a list of output fields is included in outFields. When you specify the output fields, you should limit the fields to only those you expect to use in the query or the results. The fewer fields you include, the faster the response will be. You must use the actual field names rather than the aliases (the aliases can be used in the results).
<esri:Query id="query" text="{qText.text}" returnGeometry="true"> <esri:outFields> <mx:String>CITY_NAME</mx:String> <mx:String>STATE_NAME</mx:String> </esri:outFields> </esri:Query>
In an application the query is executed based on inputs provided by the user. In the example below a panel is created with a text input for typing the name of the city to search and a button to execute the query. The click event of the button calls the doQuery() method, the first argument is the query criteria that we had previously defined and the second argument is an asynchronous responder. The responder sets the callback functions onResult() and onFault() that handles the success and failure of the query respectively.
<mx:Panel title="Search for a city" layout="horizontal" backgroundColor="0xB2BFC6" borderStyle="solid"> <mx:TextInput width="100%" id="qText" enter="doQuery()" text="San Jose"/> <mx:Button label="Do Query" click="doQuery()"/> </mx:Panel>
private function doQuery():void { queryTask.execute(query, new AsyncResponder(onResult, onFault)); }
Displaying the results of the query involves adding the symbology to the graphic and adding the graphic itself to the graphics layer. The symbology can be applied directly to a graphics layer and all graphics added to that graphics layer will then inherit that symbology.
You may remember that when we added the graphics layer we set the symbol to "infoSymbol1". The code below shows the declaration of "infoSymbol1" which is a symbol of type InfoSymbol. The InfoSymbol has an infoRenderer that defines how information is rendered. In the example below, "data.CITY_NAME" and "data.STATE_NAME" are the outfields that we previously set in the query.
If the component that you use as the infoRenderer has in its inheritance chain a parent that implements IDataRenderer then all the attributes of the graphic are available via the "data" property. In the example below the component "VBox" has a parent "Container" that implements the IDataRenderer. For more information refer to the Adobe Flex 3 Language reference.
<esri:InfoSymbol id="infoSymbol1"> <esri:infoRenderer> <mx:Component> <mx:VBox> <mx:Label text="{data.CITY_NAME}"/> <mx:Label text="{data.STATE_NAME }"/> </mx:VBox> </mx:Component> </esri:infoRenderer> </esri:InfoSymbol>
After the successful execution of the query the callback function onResult() is called. One of the arguments to the function is a FeatureSet object that contains the results of the query. The features of the FeatureSet can be directly assigned to the graphicProvider of the graphics layer to be rendered on the map.
In case of a failure the callback function onFault() is called which in the example below show an alert box with information about the failure.
private function doQuery():void { queryTask.execute(query, new AsyncResponder(onResult, onFault)); function onResult(featureSet:FeatureSet, token:Object = null ):void { myGraphicsLayer.graphicProvider = featureSet.features; } function onFault(info:Object, token:Object = null):void { Alert.show( info.toString() ); } }
The complete code for the scenario discussed in this section is below,
<?xml version="1.0" encoding="utf-8"?> <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" xmlns:esri="http://www.esri.com/2008/ags" pageTitle="Query Task" > <mx:Script> <![CDATA[ import com.esri.ags.Graphic; import com.esri.ags.tasks.FeatureSet; import mx.controls.Alert; import mx.rpc.AsyncResponder; private function doQuery():void { queryTask.execute(query, new AsyncResponder( onResult, onFault)); function onResult(featureSet:FeatureSet, token:Object = null):void { myGraphicsLayer.graphicProvider = featureSet.features; } function onFault(info:Object, token:Object = null):void { Alert.show(info.toString()); } } ]]> </mx:Script> <!-- Layer with US States --> <esri:QueryTask id="queryTask" url="http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/Specialty/ESRI_StatesCitiesRivers_USA/MapServer/0" /> <esri:Query id="query" text="{qText.text}" returnGeometry="true"> <esri:outFields> <mx:String>CITY_NAME</mx:String> <mx:String>STATE_NAME</mx:String> </esri:outFields> </esri:Query> <esri:InfoSymbol id="infoSymbol1"> <esri:infoRenderer> <mx:Component> <mx:VBox> <mx:Label text="{data.CITY_NAME }"/> <mx:Label text="{data.STATE_NAME }"/> </mx:VBox> </mx:Component> </esri:infoRenderer> </esri:InfoSymbol> <mx:Panel title="Search for a city" layout="horizontal" backgroundColor="0xB2BFC6" borderStyle="solid"> <mx:TextInput width="100%" id="qText" enter="doQuery()" text="San Jose"/> <mx:Button label="Do Query" click="doQuery()"/> </mx:Panel> <esri:Map id="map"> <esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_Imagery_World_2D/MapServer"/> <esri:GraphicsLayer id="myGraphicsLayer" symbol="{infoSymbol1}"/> </esri:Map> </mx:Application>
There is a direct correlation between performance and the number of features selected; certain queries are unrealistic or request too much data. The list below offers suggestions to enhance performance.
Using Extent |
NOTE: The following discussion assumes that you are familiar with the basic concepts of Flex.
This tutorial describes several ways to set a map's extent as well as how to retrieve the extent for use in other operations.
If you do not include extent information when you initialize a map, the default extent is used, which is the extent of the map as it was last saved in the map document. If you use multiple layers, or services, the default extent is the initial extent of the basemap or first layer added.
To set an initial extent that is different from the default extent, use the extent property or Extent class.
Your code should look similar to below.
<esri:SpatialReference id="wgs" wkid="4326"/> <esri:Extent id="extentOfKansas" xmin="-103" ymin="36" xmax="-94" ymax="41" spatialReference="{wgs}"/> <esri:Map id="myMap" extent="{extentOfKansas}"> <esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer"/> <esri:ArcGISDynamicMapServiceLayer id="myLayer" url="http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/Petroleum/KGS_OilGasFields_Kansas/MapServer" /> </esri:Map>
View another sample map extent set using the extent property.
Your code should look similar to below.
<esri:SpatialReference id="wgs" wkid="4326"/> <esri:Map id="myMap"> <esri:extent> <esri:Extent xmin="-103" ymin="36" xmax="-94" ymax="41" spatialReference="{wgs}"/> </esri:extent> <esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer"/> <esri:ArcGISDynamicMapServiceLayer id="myLayer" url="http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/Petroleum/KGS_OilGasFields_Kansas/MapServer" /> </esri:Map>
View another sample map extent set using the Extent class.
In some cases, you may want to use the extent of a layer that is not the initial layer or basemap. To do this, set the map extent to the extent of the desired layer.
In the following example, two layers are used: the base layer—ArcGIS Online world extent—and a second layer—the state of Kansas.
To set Kansas as the extent, add a load property that sets the extent of the map.
load="{myMap.extent=myKansasLayer.fullExtent}"
The load property creates the map and, when loaded, sets the full extent to the Kansas layer.
The code below sets the map extent to myKansasLayer using fullExtent.
<esri:Map id="myMap"> <esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer"/> <esri:ArcGISDynamicMapServiceLayer load="{myMap.extent=myKansasLayer.fullExtent}" id="myKansasLayer" url="http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/Petroleum/KGS_OilGasFields_Kansas/MapServer" /> </esri:Map>
NOTE: If you want to set the initial extent instead of the full extent, use myKansasLayer.initialExtent.
Retrieve the current map extent using the extent property.
The map will fire off an ExtentEvent every time the user pan or zooms the map. You can add an event listener using either mxml or ActionScript to be notified of extent changes. See for example the Event sample
<esri:Map id="myMap" extentChange="displayExtent()"> <esri:ArcGISTiledMapServiceLayer url="http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer" /> </esri:Map>
myMap.addEventListener(ExtentEvent.EXTENT_CHANGE, extentChangeHandler);
Using Graphic |
NOTE: The following discussion assumes that you are familiar with the basic concepts of Flex.
The GraphicsLayer enables overlaying graphics on top of the map. The graphics can be drawn by the user as markup or input to a task, or they can be drawn by the application in response to a task. For example, the application might add the results of a query to the map as graphics.
Graphics are not required to have all of the above items, and no one item is required. For example, many task results are returned as graphic objects in a FeatureSet. These graphics only have geometry and attributes when they are returned. If you want to add the graphics to a map, you must define a symbol for them.
If you're writing code that allows users to draw graphics on the map, the Draw toolbar can make your work easier. The Draw toolbar is a class that can help you capture the geometry that a user draws on the screen. You can then define a symbol and apply it to the geometry in a new graphic object. The drawing toolbar sample demonstrates this workflow.
The way that you add task results to the map as graphics varies by task type. If your task returns a FeatureSet, you get an array of graphics (FeatureSet.features) that you can assign to the graphicProvider of the GraphicsLayer. The code below shows how you might do this with results from QueryTask. Note that the code defines a symbol to the GraphicLayer that is assigned to all the graphics added to that layer.
private function doQuery():void { queryTask.execute(query, new AsyncResponder(onResult, onFault)); function onResult(featureSet:FeatureSet, token:Object = null):void { myGraphicsLayer.graphicProvider = featureSet.features; } function onFault(info:Object, token:Object = null):void { Alert.show( info.toString() ); } }
<esri:SimpleMarkerSymbol id="sms" size="10" color="0xFF0000" style="circle" /> <esri:GraphicsLayer id="myGraphicsLayer" symbol="{sms}"/>
Other tasks do not provide a feature set as a result but do provide the geometry, which you can use to create a graphic. For example, a Locator task finds an AddressCandidate, whose location property is a MapPoint geometry. You can use this geometry to create a graphic showing the address location, as in the code below:
for each (var candidate:AddressCandidate in candidates) { if (candidate.score > 80) { var myGraphic:Graphic = new Graphic(); myGraphic.geometry = candidate.location; myGraphic.symbol = mySymbol; myGraphic.attributes = { address: candidate.address,score: candidate.score, locatorName: candidate.attributes.Loc_name }; myGraphicsLayer.add(myGraphic); } }
See the Samples for more ideas of how to create graphics from the results of different tasks.
Symbols that are available to render the graphic are SimpleMarkerSymbol, SimpleLineSymbol, SimpleFillSymbol, PictureMarkerSymbol, PictureFillSymbol, InfoSymbol, CartographicLineSymbol and CompositeSymbol. Refer to the samples to learn how to use the different symbols.
InfoSymbols are small windows containing user interface (UI) controls and data that provide information about a point feature on a map. Unlike InfoWindows, multiple InfoSymbols can be displayed on a map at one time.
InfoSymbol has two properties infoPlacement and infoRenderer. The property infoPlacement determines the orientation of the symbol. Refer to the InfoPlacement class for the list of possible values.
The property infoRenderer is of type IFactory and can be defined as either inline or external. The infoRenderer contains the definition of UI controls to add to the InfoSymbol and the data that determines its appearance. Once the InfoSymbol has been created, it can be assigned as a graphic symbol, similar to a MarkerSymbol.
You can define infoRenderers as inline, i.e. defined in the same file as InfoSymbol.
<esri:InfoSymbol id="infoSymbol1"> <esri:infoRenderer> <mx:Component> <mx:VBox> <mx:Panel id="myPanel" height="100%" width="100%" backgroundAlpha="0" initialize="{outerDocument.initPanel(event)}"/> <mx:Button id="myButton" height="100%" width="100%" backgroundAlpha="0" click="{outerDocument.showResults()}"/> </mx:VBox> </mx:Component> </esri:infoRenderer> </esri:InfoSymbol>
Defined in a separate file from InfoSymbol, external infoRenderers are preferred because of their modular, reusable design. The external infoRenderer is defined by taking all the content that would be contained between the <mx:Component> tags and placing it in a discrete MXML or ActionScript file. An example of an infoRenderer in a separate MXML file called MyInfoRenderer.mxml will look like below.
<?xml version="1.0" encoding="utf-8"?> <mx:VBox xmlns:mx="http://www.adobe.com/2006/mxml" label="{data.STATE_NAME}" backgroundColor="0xEEEEEE"> <mx:Label text="State Fips: {data.STATE_FIPS}"/> <mx:Label text="Abbreviation: {data.STATE_ABBR}"/> <mx:Label text="Area: {data.AREA}"/> </mx:VBox>
Once defined, the infoRenderer can be used by any InfoSymbol in ActionScript or MXML.To set the infoRenderer in ActionScript, construct your code similar to the following:
var mySymbol:InfoSymbol = new InfoSymbol(); mySymbol.infoRenderer = new ClassFactory(MyInfoRenderer); myGraphic.symbol = mySymbol;
To set the infoRenderer in MXML, construct your code similar to the following:
<esri:InfoSymbol id="infoSymbol1" infoRenderer="MyInfoRenderer"/>
InfoSymbol can only be assigned to points. To add InfoSymbols to multipoints, convert them to points. To add InfoSymbols to lines or polygons, you can find a label point of the line or polygon and either change the graphic's geometry to centerpoint or create a new point graphic at the location of the centerpoint.
For example:
var polygon: Polygon; var centerPt: MapPoint; polygon = myGraphic.geometry as Polygon; centerPt = polygon.extent.center; myGraphic.geometry = centerPt;
Symbolizing graphics with renderers |
Graphics are symbolized with "symbols". Symbols can be assigned to graphics in several different ways.
Note that while you can have different geometries (for example points and lines in the same graphics layer), renderers works best when the layer only have one type of geometry.
A renderer defines a set of symbols that will be used for graphics in a graphics layer. You can use renderers to symbolize features with different colors or sizes based on a particular attribute. Here is a basic MXML example from our live samples:
<esri:SimpleMarkerSymbol id="smallSym" size="6" color="0xFF0000" alpha="0.7"/> <esri:SimpleMarkerSymbol id="mediumSym" size="10" color="0xFF0000" alpha="0.7"/> <esri:SimpleMarkerSymbol id="largeSym" size="16" color="0xFF0000" alpha="0.7"/> ... <esri:GraphicsLayer id="graphicsLayer"> <esri:renderer> <esri:ClassBreaksRenderer attribute="ranking"> <esri:ClassBreakInfo maxValue="0.33" symbol="{smallSym}"/> <esri:ClassBreakInfo minValue="0.33" maxValue="0.67" symbol="{mediumSym}"/> <esri:ClassBreakInfo minValue="0.67" symbol="{largeSym}"/> </esri:ClassBreaksRenderer> </esri:renderer> </esri:GraphicsLayer>
There are three renderers in the ArcGIS API for Flex: simple renderer, class breaks renderer, and unique value renderer. Corresponding classes are found in esri.renderer as SimpleRenderer, ClassBreaksRenderer, and UniqueValueRenderer respectively.
A simple renderer uses the same symbol for every graphic. All you have to do is specify the symbol to be used by the renderer, then apply the renderer to the graphics layer. This is equivalent to setting the symbol on the graphics layer.
<esri:GraphicsLayer id="graphicsLayer"> <esri:renderer> <esri:SimpleRenderer symbol="{smallSym}"/> </esri:renderer> </esri:GraphicsLayer>
or
<esri:GraphicsLayer id="graphicsLayer" symbol="{smallSym}"/>
A class breaks renderer symbolizes each graphic based on the value of one of its attributes. Graphics with attribute values inside the class break (a.k.a. "range") will all use the same symbol. The "breaks" define the values at which the symbology changes.
For example, suppose you have a "buildings" layer with an attribute that defines the building age. You want to symbolize buildings constructed since the year 2000 in green, buildings constructed between 1980 and 2000 in yellow, and buildings built before 1980 with red. This would be a good scenario for a class breaks renderer.
To use a class breaks renderer, you simply add one or more breaks. Each break specifies the symbol to use and the minimum and maximum values that will be used for that symbol. The example below shows how you can explicitly define breaks:
var smallSym:SimpleMarkerSymbol = new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_CIRCLE,6, 0xFF0000, 0.7); var mediumSym:SimpleMarkerSymbol = new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_CIRCLE,10, 0xFF0000, 0.7); var largeSym:SimpleMarkerSymbol = new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_CIRCLE,16, 0xFF0000, 0.7); var classBreaksRenderer:ClassBreaksRenderer = new ClassBreaksRenderer(); classBreaksRenderer.attribute = "BUILD_DATE"; var classBreakInfos:Array = [ new ClassBreakInfo(smallSym, Number.NEGATIVE_INFINITY, 1980), new ClassBreakInfo(mediumSym, 1980, 2000), new ClassBreakInfo(largeSym, 2000, Number.POSITIVE_INFINITY) ]; classBreaksRenderer.infos = classBreakInfos; graphicsLayer.renderer = classBreaksRenderer;
Note that if there is no maximum limit on a break, you can use "Number.POSITIVE_INFINITY" for the maximum value. Similarly, you can use "Number.NEGATIVE_INFINITY" when there is no minimum.
Any value that is greater than or equal to the minimum will be included in the break. Any value that is less than the maximum will be included in the break. Thus, if you have two breaks 0 - 10 and 10 - 20, the value 10 would fall in the second break (10 - 20). Avoid creating overlapping breaks or gaps between breaks.
You can also define breaks mathematically. For example, you can do some basic arithmetic to ensure that each break falls an equal distance apart given the input data (sometimes known as an "equal interval" classification):
var numRanges : int = 10; var breaks:Number = (max - min) / numRanges; for (var i:int = 0; i < numRanges; i++) { classBreakInfos.push(new ClassBreakInfo( new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_CIRCLE, (i+1)*5, 0xFF0000, 0.7), min + (i*breaks), min + ((i+1)*breaks) ) ); }
A unique value renderer symbolizes groups of graphics that have matching attributes. For example, you could use a unique value renderer to symbolize zoning designations: red for "Residential", green for "Industrial", blue for "Commercial", and so on.
To define a unique value renderer you specify the attribute on which to base it on, and an optional defaultSymbol for values that are not covered by a specific UniqueValueInfo. Each "UniqueValueInfo" contains the specific value and symbol to use for each "unique value".
<esri:SimpleFillSymbol id="rFill" alpha="0.5" color="0xFF0000"/> <esri:SimpleFillSymbol id="gFill" alpha="0.5" color="0x00FF00"/> <esri:SimpleFillSymbol id="bFill" alpha="0.5" color="0x0000FF"/> <esri:UniqueValueRenderer id="uniqueValueRenderer" attribute="ZONING"> <esri:UniqueValueInfo value="Residential" symbol="{rFill}"/> <esri:UniqueValueInfo value="Industrial" symbol="{gFill}"/> <esri:UniqueValueInfo value="Commercial" symbol="{bFill}"/> </esri:UniqueValueRenderer>
The equivalent code with ActionScript:
var rFill:SimpleFillSymbol = new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID, 0xFF0000, 0.5); var gFill:SimpleFillSymbol = new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID, 0x00FF00, 0.5); var bFill:SimpleFillSymbol = new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID, 0x0000FF, 0.5); var uniqueValuerenderer:UniqueValueRenderer = new UniqueValueRenderer(); uniqueValuerenderer.attribute = "ZONING"; var uniqueValueInfos:Array =[]; uniqueValueInfos.push(new UniqueValueInfo(rFill, "Residential")); uniqueValueInfos.push(new UniqueValueInfo(gFill, "Industrial")); uniqueValueInfos.push(new UniqueValueInfo(bFill, "Commercial")); uniqueValuerenderer.infos = uniqueValueInfos; graphicsLayer.renderer = uniqueValuerenderer;
Values that you don't add to the list are not drawn - unless you specify a defaultSymbol on the UniqueValueRenderer, in which case those graphics will be drawn with the default symbol.
Geoprocessing tasks |
Geoprocessing allows you to automate your GIS analyses by creating custom tools and linking them within ArcGIS. You can arrange these tools in a logical way to accomplish a multistep task in a single operation rather than a series of manually run tools.
The Geoprocessor class in the ArcGIS API for Flex gives you access to various geoprocessing tasks, which are exposed through services in the ArcGIS Server Services Directory.
To use the geoprocessing services, obtain the following information from the Services Directory:
The Services Directory links to all available services. The image below shows a sample geoprocessing service:
From this page, you can see that the geoprocessing service ESRI_Elevation_World is located in the Elevation folder and runs on sampleserver1.arcgisonline.com.
The following appears when you click the Viewshed geoprocessing model:
To execute this geoprocessing task, copy and paste this MXML code into your application:
<esri:Geoprocessor id="gp" url="http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/Elevation/ESRI_Elevation_World/GPServer/Viewshed" />
The equivalent code with ActionScript:
var gp:Geoprocessor = new Geoprocessor("http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/Elevation/ESRI_Elevation_World/GPServer/Viewshed");
The parameters in the Services Directory show the required inputs and outputs of the task. In the example above, you need to supply all parameters whose Direction is esriGPParameterDirectionInput and whose Parameter Type is esriGPParameterTypeRequired.
You do not have to supply the output parameters because the output is always returned as an array of ParameterValue.
For instance, the input parameters might look like:
var params:Object = "Input_Observation_Point":featureSet, "Viewshed_Distance":vsDistance );
The way you run the task depends on whether the geoprocessing task is synchronous or asynchronous.
In the case of synchronous execution, the client executes the task and waits for a response before proceeding. The Supported Operations section of the Services Directory displays "Execute Task" for synchronous tasks.
In an asynchronous execution, the client submits a job, then verifies that it was successful using a unique job ID. When the task completes, the client can retrieve the results. The Supported Operations section of the Services Directory displays "Submit Job" for asynchronous tasks.
Routing tasks |
When you work with the RouteTask, you'll follow the general pattern of:
When you create an instance of RouteTask, you provide a URL that is the REST endpoint to an ArcGIS Server network analysis service. You can copy and paste this MXML code into your application:
<esri:RouteTask id="routeTask" url="http://tasks.arcgisonline.com/ArcGIS/rest/services/NetworkAnalysis/ESRI_Route_NA/NAServer/Route" />
The equivalent code with ActionScript:
var routeTask:RouteTask = new RouteTask ("http://tasks.arcgisonline.com/ArcGIS/rest/services/NetworkAnalysis/ESRI_Route_NA/NAServer/Route");
In order to get the results you want from the route task, you need to specify the details of your routing problem such as stop locations, barrier locations, the impedance attribute, etc. You do this using RouteParameters. The example below shows how you'd use RouteParameters to define two stops for a route using ActionScript only. See the Route samples for a mix of MXML and ActionScript.
var routeParams:RouteParameters = new RouteParameters(); var stop1:Graphic = new Graphic(new MapPoint(-117.21,34.065); var stop2:Graphic = new Graphic(new MapPoint(-117.185,34.05); var stops:FeatureSet = new FeatureSet([ stop1, stop2]); routeParams.stops = stops;
For a complete description of each route parameter, see the RouteParameters entry in the API reference.
Once you've created the route task and configured its parameters, you can call RouteTask.solve() to solve the route.
routeTask.solve(routeParams);
In addition to calling the solve method, you need to handle the solveComplete and fault events on the RouteTask. These functions define what the application will do with the results, whether the result is a route or an error message.
<esri:RouteParameters id="routeParams" solveComplete="solveCompleteHandler(event)" fault="faultHandler(event)" />
The equivalent code with ActionScript:
routeTask.addEventListener(RouteEvent.SOLVE_COMPLETE, solveCompleteHandler); routeTask.addEventListener(FaultEvent.FAULT, faultHandler);
Either way, you would usually create the actual functions as:
private function solveCompleteHandler(event:RouteEvent):void { var routeResult:RouteResult = event.routeSolveResult.routeResults[0]; ... } private function faultHandler(event:FaultEvent):void { Alert.show(event.fault.faultString, "Routing Error"); }
The RouteTask can help you find the most efficient path for visiting a given list of stops. This is sometimes known as the traveling salesperson problem. To solve it, set RouteParameters.findBestSequence to true and the stops will be visited in the most efficient order. You can optionally designate whether the first and last stops on the list should remain fixed or not.
routeParams.findBestSequence = true; //routeParams.preserveFirstStop = true; //routeParams.preserveLastStop = true;
The RouteTask can return turn-by-turn driving directions between stops. To get the directions, set RouteParameters.returnDirections to true.
routeParams.returnDirections = true;
Batch routing, i.e. solving multiple routes in one request is also possible. Stops with same name will be grouped into sets for solving individual routes. For the batch routing result, you'll get an array of RouteResults containing each route.
Constrain stop visits to certain times of day, or time windows - for in-depth information on how time windows work, see Routing with time windows in the ArcGIS Desktop Help.
Styling Components |
The API along with its classes has UI components that can be customized to suit your application needs.
Styles are the visual properties of components such as size, color, etc. A style can be applied to all instances of a component using a Type Selector style or just individual instances using a Class Selector style. In Flex the style definition is declared within the <mx:Style> tag. The style properties that are available for modification for a component can be found in the API reference. The components that can be styled are found under the package com.esri.controls.
On this page we will show how to style three different components:
Navigation — The navigation control is used to display layers at predefined scales. The default navigation control is as shown in Figure 1. It consists of a VSlider and a plus and minus button. The default look of the navigation control (Figure 1) can be changed to suit your project. The section below shows how to style the navigation control as shown in Figure 2. See the Styling zoom slider with CSS sample.
Figure 1 - default navigation control. |
Figure 2 - styled navigation control. |
The class com.esri.ags.controls.Navigation represents the Navigation control. The control supports a set of style classes that can be used to provide a different appearance to the slider. The style classes used by the navigation control are,
The style below will place the slider at a distance of 30 pixels from the top and right margin of the Map. Since the property left is a default property you will have to use the value NaN so that the value of property left is not used.
Navigation { top: 30; right: 30; left: NaN; }
The style below sets the different states of the NavigationMinusButton. These properties are standard style properties of a Button. In this case the button is assigned an image of a globe.
NavigationMinusButton { disabledSkin: Embed(source="assets/globe_icon.png"); downSkin: Embed(source="assets/globe_icon.png"); overSkin: Embed(source="assets/globe_icon.png"); upSkin: Embed(source="assets/globe_icon.png"); }
The style below sets the different states of the NavigationPlusButton. These properties are standard style properties of a Button. In this case the button is assigned an image of a home.
NavigationPlusButton { disabledSkin: Embed(source="assets/home_icon.png"); downSkin: Embed(source="assets/home_icon.png"); overSkin: Embed(source="assets/home_icon.png"); upSkin: Embed(source="assets/home_icon.png"); }
The style below defines the appearance of the slider. Except for the property show-scale-in-data-tip all other properties are inherited from a VSlider.
NavigationSlider { show-scale-in-data-tip:false; /*display tile level instead of scale */ dataTipPlacement: "left"; show-track-highlight: true; tick-color: #ffffff; } ToolTip { backgroundAlpha: 1.0; backgroundColor: haloBlue; fontWeight: bold; color: white; }
InfoSymbol – These are callouts that are used to display content, usually the results of a query. InfoSymbols can only be used with a graphic of type MapPoint. The class InfoSymbolContainer represents style that is used to render the InfoSymbol.
The callout in figure 3 is displayed with the default style. To change the style use a CSS class called InfoSymbolContainer and set the appropriate values. The InfoSymbolContainer inherits mx.core.container hence all the style properties that can be applied on an mx.controls.container can be used.
Figure 3 - default InfoSymbol. |
Figure 4 - styled InfoSymbol. |
The style below represents the style as it is displayed in Figure 4,
InfoSymbolContainer { backgroundColor: #FF530D; backgroundAlpha: 1.0; font-style: italic; font-weight: bold; font-size: 12; }
Adding behaviors to infosymbols – In addition to adding styling properties, behaviors can also be added to the infoSymbols. The figures below show an example of a infoSymbol with a user-defined behavior. The Figures 6 and 7 show the mouse hover and mouse click behavior of the infoSymbol. This example takes advantage of the States feature of the Flex framework to assign behavior. See the InfoSymbol with States sample for more information on how this behavior is implemented.
Figure 5 - default state of InfoSymbol with user-defined behavior. |
Figure 6 - hover (or mouse over) state of InfoSymbol with user-defined behavior. |
Figure 7 - state of InfoSymbol with user-defined behavior after click. |
ScaleBar – the scalebar supports two styling properties. They are fillColor and outlineColor. The default ScaleBar style is shown in Figure 8. The scale bar shown in Figure 9 uses the style properties below.
ScaleBar { fillColor: #FF530D; outlineColor: #FFFFFF; }
Figure 8 - default scale bar. |
Figure 9 - styled scale bar. |