Identify features on the map

In a typical identify operation, a user clicks the map and obtains information about any features at that clicked point. ArcGIS Runtime SDK for Java provides the IdentifyTask class to perform this type of search. Use the identify task to search a particular service's layers for features that intersect an input geometry. Once the matching features are returned, you can display their geometries and attributes in your application. An identify operation has the potential to retrieve a lot of information, but you can limit the scope of the search or the amount of information returned for each result by controlling the identify parameters.

Use the IdentifyTask class

To identify features on a map, complete the following steps:

  1. Instantiate the IdentifyTask class and provide the URL of the map service to the task's constructor.
  2. Specify the input parameters to the task.
  3. Execute the task synchronously or asynchronously.
  4. Listen for the completion of the task and process the results.

These steps are explained in further detail below.

Instantiate the IdentifyTask class

First, obtain the URL of the map service containing the layers in which to identify features.

The following code shows the URL to an online map service, in this case the ESRI_Census_USA map service.

String mapServiceURL = 
  "http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/" +
  "Demographics/ESRI_Census_USA/MapServer";

The following code snippet shows how to obtain the URL to a Local Server map service created from a map package.

// create a local dynamic layer from the path to a map package
ArcGISLocalDynamicMapServiceLayer localDynamicLayer = 
  new ArcGISLocalDynamicMapServiceLayer("c:/data/mpks/MyMapPackage.mpk");

// initialize the layer, for example by adding it to a map
jMap.getLayers().add(localDynamicLayer);

// get the URL from the initialized layer
dynamicLayer.addLayerInitializeCompleteListener(
    new LayerInitializeCompleteListener() {

      @Override
      public void layerInitializeComplete(LayerInitializeCompleteEvent e) {
        if (e.getLayer().getStatus() == LayerStatus.INITIALIZED) {
          // get the URL to the local map service
          String mapServiceURL = dynamicLayer.getUrl();
        }
      }
    });

Second, instantiate the IdentifyTask class, passing the map service URL to the task's constructor. If the map service is secured, pass user credentials for the service as a second parameter.

// unsecured map service
IdentifyTask identifyTask = new IdentifyTask(mapServiceURL);

// secured map service
UserCredentials credentials = new UserCredentials();
...
IdentifyTask identifyTask = new IdentifyTask(mapServiceURL, credentials);

Specify the input parameters

The IdentifyParameters class defines how you want the identify task to operate. Specify the parameters, then pass this class into the IdentifyTask constructor. The following are some basic guidelines:

  • Identify operates by intersecting a geometry with the features in one or more layers. Provide the intersection geometry by calling setGeometry.
  • Control the distance (in pixels) from your geometry to perform the intersection by calling setTolerance.
  • Identify can be performed on any of the layers. Specify the layers, by ID, that take part in the identify operation by calling setLayers(int[]). Specify either the visible layers, the top most layer, or all layers.

IdentifyParameters identifyparam = new IdentifyParameters(); 
identifyparam.setGeometry(geometry); 
identifyparam.setMapExtent(map.getExtent()); 
identifyparam.setSpatialReference(map.getSpatialReference()); 
identifyparam.setMapHeight(map.getHeight()); 
identifyparam.setMapWidth(map.getWidth()); 
identifyparam.setLayerMode(IdentifyParameters.VISIBLE_LAYERS); 
identifyparam.setTolerance(10);

Execute the task

Execute the IdentifyTask asynchronously or synchronously. If you execute the task asynchronously, the application will remain responsive during the execution of the task. This is the recommended method of execution for most identify operations. If you execute the task synchronously (on the application thread), the application will be paused while the task is executing. This method of execution is only recommended if the identify task is reliably fast and the result list is small.

Asynchronous execution

Asynchronous execution of the identify task is performed using the execute method which takes two parameters: the previously defined IdentifyParameters instance and a CallbackListener. Set up a callback listener to respond when the task completes or throws an error. If the task completes successfully, results are returned in an array of IdentifyResults via the callback.

identifyTask.execute(identifyparam, new CallbackListener<IdentifyResult[]>(){ 
 
  @Override 
  public void onError(Throwable e){ 
    // handle/display error as desired
  } 
 
  @Override 
  public void onCallback(IdentifyResult[] identifyResults) {
    // go through the returned result array
    for (int i = 0; i < identifyResults.length; i++) { 
      IdentifyResult result = identifyResults[i]; 
      String resultString = 
        result.getAttributes().get(result.getDisplayFieldName()) 
        + " (" + result.getLayerName() + ")"; 
    }
  } 
});

Synchronous execution

Synchronous execution of the identify task is performed using the execute method which takes the previously defined IdentifyParameters instance as input. This synchronous method returns an array of IdentifyResults that can be examined by the application.

IdentifyResult[] results = task.execute(identifyparam);
for (int i = 0; i < identifyResults.length; i++) {
  IdentifyResult result = identifyResults[i];
  String resultString = 
    result.getAttributes().get(result.getDisplayFieldName()) 
    + " (" + result.getLayerName() + ")";
});

Process the results

The results of the Identify task are returned in an array of IdentifyResult objects. Each item in the array represents a feature containing one geometry and one or more attributes with their values. Once you have the IdentifyResult collection, process its contents as in the following code sample:

for (int i = 0; i < identifyResults.length; i++) {

  IdentifyResult result = identifyResults[i];

  ... = result.getLayerName();
  ... = result.getDisplayFieldName();
  ... = result.getGeometry();
  ... = result.getAttributes();

});

Sample code

To view any samples related to searching data, launch the ArcGIS Runtime SDK for Java sample viewer application installed with the SDK. Explore the interactive samples and their code in the Search section.