Select to view content in your preferred language

Specify fields in Identify Parameters

3006
10
Jump to solution
05-22-2012 11:35 AM
TanyaOwens
Frequent Contributor
Hello,

I have found a way to specify which layers I want to show using the identify task by using identifyParams.LayerIds.AddRange(new int[] {4, 9, 1,});. is there a way to select out the fields I want to display from these selected layers?

Thanks!
0 Kudos
1 Solution

Accepted Solutions
JenniferNery
Esri Regular Contributor
Identify is an operation on map service, the current parameters that is exposed by REST API does not include fields. This is the reason why you get all fields.

From your Silverlight application though, even when service returned all fields, you can still exclude other fields when displaying the result.

You can modify your existing code this way:
var fieldsToDisplay = new List<string>() {"fieldName1", fieldName2"};
var attributesToDisplay = new Dictionary<string, object>();
foreach(var item in selectedFeature.Attributes)
     if(fieldsToDisplay.Contains(item.Key))
          attributesToDisplay[item.Key]= item.Value;
IdentifyDetailsDataGrid.ItemsSource = attributesToDisplay;

View solution in original post

0 Kudos
10 Replies
JenniferNery
Esri Regular Contributor
This is a question for REST API. I believe this is new to 10.1, in "dynamicLayers", you can specify "fields". In pre-10, you will get all fields but your Silverlight application can only show a subset of them. You can modify the following SDK sample: http://help.arcgis.com/en/webapi/silverlight/samples/start.htm#Identify

Instead of this line:
Data = feature.Attributes


You can create temporary variable that will hold attributes
var temp = new Dictionary<string, object>();
var fields = new List<string>() {"field1", "field2"}; //fields to display
foreach(var item in feature.Attributes)
{
     if(fields.Contains(item.Key)) 
          temp[item.Key] = item.Value;
}
//more code goes here
     Data = temp
0 Kudos
TanyaOwens
Frequent Contributor
Forgive me I am very new to Silverlight, but I don't understand why this is a rest API question. I modified the identify task code from the concepts in the Silverlight API resource center http://help.arcgis.com/en/webapi/silverlight/help/index.html#/Identify_task/01660000001m000000/. In the c# code behind is where I selected out the layer from the service I am using. I would like to use the code to show only a few of the field attributes, not all of them - right now my code displays all of them. I am not sure where in the code I have to add in the code you provided. Below is the current code I am using.  Thanks for your help.     


            //Identify Parameters for Location to Address Point
            ESRI.ArcGIS.Client.Tasks.IdentifyParameters identifyParams = new IdentifyParameters
            {
                //This is where the xy coords are passed into the parameters
                Geometry = address.Location,
                MapExtent = MyMap.Extent,
                Width = (int)MyMap.ActualWidth,
                Height = (int)MyMap.ActualHeight,
                LayerOption = LayerOption.all,
                SpatialReference = MyMap.SpatialReference
            };

            identifyParams.LayerIds.AddRange(new int[] { 4, 9, 1, });

            IdentifyTask identifyTask = new IdentifyTask("http://gismaps.pagnet.org/ArcGIS/rest/services/SchoolSearch_102710/MapServer");
            identifyTask.ExecuteCompleted += IdentifyTask_ExecuteCompleted;
            identifyTask.Failed += IdentifyTask_Failed;
            identifyTask.ExecuteAsync(identifyParams);


        }

        // Notify the user if the task fails to execute.
        private void LocatorTask_Failed(object sender, TaskFailedEventArgs e)
        {
            MessageBox.Show("Locator service failed: " + e.Error);
        }
               
        //Displaying Identify Results.
        private void IdentifyTask_ExecuteCompleted(object sender, IdentifyEventArgs args)
        {
            IdentifyComboBox.Items.Clear();

            if (args.IdentifyResults.Count > 0)
            {
                IdentifyResultsStackPanel.Visibility = Visibility.Visible;

                foreach (IdentifyResult result in args.IdentifyResults)
                {
                    string title = string.Format("{0} ({1})", result.Value.ToString(), result.LayerName);
                    IdentifyComboBox.Items.Add(title);
                }

                IdentifyComboBox.UpdateLayout();

                _lastIdentifyResult = args.IdentifyResults;

                IdentifyComboBox.SelectedIndex = 0;
            }
            else
            {
                IdentifyResultsStackPanel.Visibility = Visibility.Collapsed;
                MessageBox.Show("No features found");
            }

        }

        // Show geometry and attributes of the selected feature.
        void IdentifyComboBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            // Clear previously selected feature from GraphicsLayer.
            GraphicsLayer graphicsLayer = MyMap.Layers["ResultsGraphicsLayer"] as GraphicsLayer;
            graphicsLayer.ClearGraphics();

            // Check that ComboBox has a selected item. This is needed because SelectionChanged fires
            // when ComboBox.Clear is called.
            if (IdentifyComboBox.SelectedIndex > -1)
            {
                // Update DataGrid with the selected feature's attributes.
                Graphic selectedFeature = _lastIdentifyResult[IdentifyComboBox.SelectedIndex].Feature;


                IdentifyDetailsDataGrid.ItemsSource = selectedFeature.Attributes;

                // Apply the symbol and add the selected feature to the map.
                selectedFeature.Symbol = LayoutRoot.Resources["SelectedFeatureSymbol"] as ESRI.ArcGIS.Client.Symbols.Symbol;
                graphicsLayer.Graphics.Add(selectedFeature);
            }
        }
0 Kudos
JenniferNery
Esri Regular Contributor
Identify is an operation on map service, the current parameters that is exposed by REST API does not include fields. This is the reason why you get all fields.

From your Silverlight application though, even when service returned all fields, you can still exclude other fields when displaying the result.

You can modify your existing code this way:
var fieldsToDisplay = new List<string>() {"fieldName1", fieldName2"};
var attributesToDisplay = new Dictionary<string, object>();
foreach(var item in selectedFeature.Attributes)
     if(fieldsToDisplay.Contains(item.Key))
          attributesToDisplay[item.Key]= item.Value;
IdentifyDetailsDataGrid.ItemsSource = attributesToDisplay;
0 Kudos
TanyaOwens
Frequent Contributor
That worked perfectly, Thank you!
0 Kudos
TanyaOwens
Frequent Contributor
This is a question for REST API. I believe this is new to 10.1, in "dynamicLayers", you can specify "fields". In pre-10, you will get all fields but your Silverlight application can only show a subset of them. You can modify the following SDK sample: http://help.arcgis.com/en/webapi/silverlight/samples/start.htm#Identify

Instead of this line:
Data = feature.Attributes


You can create temporary variable that will hold attributes
var temp = new Dictionary<string, object>();
var fields = new List<string>() {"field1", "field2"}; //fields to display
foreach(var item in feature.Attributes)
{
     if(fields.Contains(item.Key)) 
          temp[item.Key] = item.Value;
}
//more code goes here
     Data = temp


Hi Jennifer,

I ended up changing my code to use the identify code from the sample so I came back to this issue of selecting field out. The above code is not working for me. When I place the variable porting of the code above  the Data = temp I end up getting an error about the feature.Attributes not be referenced. When I place it below, I get an error about the temp not being defined. If I just replace the feature.Attributes with this code it also gives me an error. Can you give me more guidance about the actual location for this code.

Thanks!
0 Kudos
TanyaOwens
Frequent Contributor
To clarify by difficulties with this - with the following code I get an "Cannot use local variable 'feature' before it is declared"
        public void ShowFeatures(List<IdentifyResult> results)
        {
            _dataItems = new List<DataItem>();

            if (results != null && results.Count > 0)
            {
                //IdentifyComboBox.Items.Clear();
                foreach (IdentifyResult result in results)
                {
                    var temp = new Dictionary<string, object>();
                    var fields = new List<string>() { "School Name", "Address", "Zip", "Phone", "Website", "School District" }; //fields to display
                    foreach (var item in feature.Attributes)
                    {
                        if (fields.Contains(item.Key))
                            temp[item.Key] = item.Value;
                    }
                    Graphic feature = result.Feature;
                    string title = result.Value.ToString() + " (" + result.LayerName + ")";
                    _dataItems.Add(new DataItem()

                    {
                        
                        Title = title,
                        Data = temp

                    });
                    //IdentifyComboBox.Items.Add(title);


                    if (result.LayerId == 4)
                        IdentifyDetailsDataGrid.ItemsSource = feature.Attributes;

                    if (result.LayerId == 9)
                        IdentifyDetailsDataGrid2.ItemsSource = feature.Attributes;

                    if (result.LayerId == 14)
                        IdentifyDetailsDataGrid3.ItemsSource = feature.Attributes;

                }


The following does NOT have any errors but does not select out the field requested (all fields still show)
        public void ShowFeatures(List<IdentifyResult> results)
        {
            _dataItems = new List<DataItem>();

            if (results != null && results.Count > 0)
            {
                //IdentifyComboBox.Items.Clear();
                foreach (IdentifyResult result in results)
                {

                    Graphic feature = result.Feature;
                    var temp = new Dictionary<string, object>();
                    var fields = new List<string>() { "School Name", "Address", "Zip", "Phone", "Website", "School District" }; //fields to display
                    foreach (var item in feature.Attributes)
                    {
                        if (fields.Contains(item.Key))
                            temp[item.Key] = item.Value;
                    }
                    string title = result.Value.ToString() + " (" + result.LayerName + ")";
                    _dataItems.Add(new DataItem()

                    {
                        
                        Title = title,
                        Data = temp

                    });
                    //IdentifyComboBox.Items.Add(title);


                    if (result.LayerId == 4)
                        IdentifyDetailsDataGrid.ItemsSource = feature.Attributes;

                    if (result.LayerId == 9)
                        IdentifyDetailsDataGrid2.ItemsSource = feature.Attributes;

                    if (result.LayerId == 14)
                        IdentifyDetailsDataGrid3.ItemsSource = feature.Attributes;

                }


The following get a lot of errors including syntax errors as well as "does not contain a definition for 'temp'"

        public void ShowFeatures(List<IdentifyResult> results)
        {
            _dataItems = new List<DataItem>();

            if (results != null && results.Count > 0)
            {
                //IdentifyComboBox.Items.Clear();
                foreach (IdentifyResult result in results)
                {

                    Graphic feature = result.Feature;

                    string title = result.Value.ToString() + " (" + result.LayerName + ")";
                    _dataItems.Add(new DataItem()



                    {
                    var temp = new Dictionary<string, object>();
                    var fields = new List<string>() { "School Name", "Address", "Zip", "Phone", "Website", "School District" }; //fields to display
                    foreach (var item in feature.Attributes)
                    {
                        if (fields.Contains(item.Key))
                            temp[item.Key] = item.Value;
                    }
                        Title = title,
                        Data = temp

                    });
                    //IdentifyComboBox.Items.Add(title);


                    if (result.LayerId == 4)
                        IdentifyDetailsDataGrid.ItemsSource = feature.Attributes;

                    if (result.LayerId == 9)
                        IdentifyDetailsDataGrid2.ItemsSource = feature.Attributes;

                    if (result.LayerId == 14)
                        IdentifyDetailsDataGrid3.ItemsSource = feature.Attributes;

                }
                //IdentifyComboBox.SelectedIndex = 0;
            }
        }
0 Kudos
TanyaOwens
Frequent Contributor
Never mind, I got it with the following code:

        public void ShowFeatures(List<IdentifyResult> results)
        {
            _dataItems = new List<DataItem>();

            if (results != null && results.Count > 0)
            {
                
                foreach (IdentifyResult result in results)
                {

                    Graphic feature = result.Feature;
                    string title = result.Value.ToString() + " (" + result.LayerName + ")";
                    _dataItems.Add(new DataItem()

                    {

                        Title = title,
                        Data = feature.Attributes

                    });
                    
                    var fieldsToDisplay = new List<string>() { "School Name", "Address", "Zip", "Phone", "Website", "School District" };
                    var attributesToDisplay = new Dictionary<string, object>();
                    foreach (var item in feature.Attributes)
                        if (fieldsToDisplay.Contains(item.Key))
                            attributesToDisplay[item.Key] = item.Value;
                    

                    if (result.LayerId == 4)
                        IdentifyDetailsDataGrid.ItemsSource = feature.Attributes;
                        IdentifyDetailsDataGrid.ItemsSource = attributesToDisplay;
                    if (result.LayerId == 9)
                        IdentifyDetailsDataGrid2.ItemsSource = feature.Attributes;
                        IdentifyDetailsDataGrid2.ItemsSource = attributesToDisplay;  
                    if (result.LayerId == 14)
                        IdentifyDetailsDataGrid3.ItemsSource = feature.Attributes;
                        IdentifyDetailsDataGrid3.ItemsSource = attributesToDisplay;

                }


Now all I need it to set the field attribute of "Website" to be a hyperlink in all three data grids.
0 Kudos
TanyaOwens
Frequent Contributor
Never mind, I got it with the following code:

        public void ShowFeatures(List<IdentifyResult> results)
        {
            _dataItems = new List<DataItem>();

            if (results != null && results.Count > 0)
            {
                
                foreach (IdentifyResult result in results)
                {

                    Graphic feature = result.Feature;
                    string title = result.Value.ToString() + " (" + result.LayerName + ")";
                    _dataItems.Add(new DataItem()

                    {

                        Title = title,
                        Data = feature.Attributes

                    });
                    
                    var fieldsToDisplay = new List<string>() { "School Name", "Address", "Zip", "Phone", "Website", "School District" };
                    var attributesToDisplay = new Dictionary<string, object>();
                    foreach (var item in feature.Attributes)
                        if (fieldsToDisplay.Contains(item.Key))
                            attributesToDisplay[item.Key] = item.Value;
                    

                    if (result.LayerId == 4)
                        IdentifyDetailsDataGrid.ItemsSource = feature.Attributes;
                        IdentifyDetailsDataGrid.ItemsSource = attributesToDisplay;
                    if (result.LayerId == 9)
                        IdentifyDetailsDataGrid2.ItemsSource = feature.Attributes;
                        IdentifyDetailsDataGrid2.ItemsSource = attributesToDisplay;  
                    if (result.LayerId == 14)
                        IdentifyDetailsDataGrid3.ItemsSource = feature.Attributes;
                        IdentifyDetailsDataGrid3.ItemsSource = attributesToDisplay;

                }


Now all I need it to set the field attribute of "Website" to be a hyperlink in all three data grids.


I spoke too soon!!! The above code only returns data from layer 14 in all three data grids (although it does show my selected fields in each grid - the attributes are all from one layer)
0 Kudos
TanyaOwens
Frequent Contributor
Fixed it!!!

        public void ShowFeatures(List<IdentifyResult> results)
        {
            _dataItems = new List<DataItem>();

            if (results != null && results.Count > 0)
            {
                
                foreach (IdentifyResult result in results)
                {

                    Graphic feature = result.Feature;
                    string title = result.Value.ToString() + " (" + result.LayerName + ")";
                    _dataItems.Add(new DataItem()

                    {

                        Title = title,
                        Data = feature.Attributes

                    });

                    var fieldsToDisplay = new List<string>() { "School Name", "Address", "Zip", "Phone", "Website", "School District" };
                    var attributesToDisplay = new Dictionary<string, object>();
                    foreach (var item in feature.Attributes)
                        if (fieldsToDisplay.Contains(item.Key))
                            attributesToDisplay[item.Key] = item.Value;
                    

                    if (result.LayerId == 4)
                        IdentifyDetailsDataGrid.ItemsSource = attributesToDisplay;
                    if (result.LayerId == 9)                       
                        IdentifyDetailsDataGrid2.ItemsSource = attributesToDisplay;  
                    if (result.LayerId == 14)                        
                        IdentifyDetailsDataGrid3.ItemsSource = attributesToDisplay;

                }
                //IdentifyComboBox.SelectedIndex = 0;
            }
0 Kudos