C# Code for ArcGIS Pro Add-in to retrieve text string from selected record of a layer

312
2
Jump to solution
11-29-2021 05:40 PM
JohnHanson1
New Contributor

Learning C# and I am looking for some code that will allow me to create a tool for the Map View, that when positioned over an individual polygon and selected by the tool, would return the text string (e.g. CntyGeo.lyrx) from the attribute field (say "Link") of the selected feature layer in the Contents Pane.
I would use this returned individual text string to reference to another C# code that adds a .lyrx file to the Map View (see C# code below). The text string would be used to add an .lyrx from the C:\ drive (e.g. CntyGeo.lyrx) to the Map View which currently works:
protected override void OnClick()
{
try { QueuedTask.Run(() => { Uri myUri = new Uri(@"C:\Temp\CntyGeo.lyrx"); Layer newlayer = LayerFactory.Instance.CreateFeatureLayer(myUri, MapView.Active.Map, LayerPosition.AddToTop); }); }
catch (Exception ex)
{
MessageBox.Show($@"Error: {ex.ToString()}");
}
I'm using ArcGIS Pro 2.8 and MS Visual Studio 2019. Thanks for any help.

Regards,

John

0 Kudos
2 Solutions

Accepted Solutions
KirkKuykendall1
Occasional Contributor III

Something like this might work.

Right click on project and Add>New Item then choose Pro Map Tool.

KirkKuykendall1_1-1638891317521.png

 

In the daml, change the condition:

KirkKuykendall1_0-1638891124870.png

 

Change the OnSketchCompleteAsync override:

 

using ArcGIS.Core.CIM;
using ArcGIS.Core.Data;
using ArcGIS.Core.Geometry;
using ArcGIS.Desktop.Editing;
using ArcGIS.Desktop.Framework.Threading.Tasks;
using ArcGIS.Desktop.Mapping;
using System;
using System.Diagnostics;
using System.Linq;
using System.Threading.Tasks;

namespace ToolTester
{
    internal class MapTool1 : MapTool
    {
        public MapTool1()
        {
            IsSketchTool = true;
            SketchType = SketchGeometryType.Point;
            SketchOutputMode = SketchOutputMode.Map;
        }

        protected override Task OnToolActivateAsync(bool active)
        {
            return base.OnToolActivateAsync(active);
        }

        protected override Task<bool> OnSketchCompleteAsync(Geometry geometry)
        {
            return QueuedTask.Run(() =>
            {
                var fLayer = this.ActiveMapView.GetSelectedLayers().FirstOrDefault() as FeatureLayer;
                //condition="esri_mapping_featureLayerSelectedCondition" in the daml should prevent this ...
                if (fLayer == null)
                    return true;
                //use whatever field is been set as Display Field in the layer properties ...
                var fldName = ((CIMFeatureLayer)fLayer.GetDefinition()).FeatureTable.DisplayField;
                string fileName = GetFirstRow(fLayer, fldName, geometry);
                if (!string.IsNullOrWhiteSpace(fileName))
                {
                    Uri myUri = new Uri($@"C:\Temp\{fileName}.lyrx");
                    Debug.Print(fileName);
                    //todo: verify file exists, layer not already added, etc.
                    //Layer newlayer = LayerFactory.Instance.CreateFeatureLayer(myUri, this.ActiveMapView.Map, LayerPosition.AddToTop);
                }
                return true;
            });
        }
        private string GetFirstRow(FeatureLayer fLayer, string fldName, Geometry geom)
        {
            string s = "";
            GeometryEngine.Instance.Project(geom, fLayer.GetSpatialReference());
            using (var cursor = fLayer.Search(new SpatialQueryFilter()
            {
                FilterGeometry = GeometryEngine.Instance.Project(geom, fLayer.GetSpatialReference()),
                SpatialRelationship = SpatialRelationship.Intersects,
                SubFields = fldName
            }))
            {
                if (cursor.MoveNext())
                    s = cursor.Current[fldName].ToString();
            };
            return s;
        }
    }
}

 

 

View solution in original post

JohnHanson1
New Contributor

Mr. Kuykendall,

Perfect!  Thank you very much!  I had added some C# code to add layers from a selection, and it works like a charm.  I attached the modified code of the MapTool1.cs (zipped) below.

Once again, Thank you

John Hanson

View solution in original post

0 Kudos
2 Replies
KirkKuykendall1
Occasional Contributor III

Something like this might work.

Right click on project and Add>New Item then choose Pro Map Tool.

KirkKuykendall1_1-1638891317521.png

 

In the daml, change the condition:

KirkKuykendall1_0-1638891124870.png

 

Change the OnSketchCompleteAsync override:

 

using ArcGIS.Core.CIM;
using ArcGIS.Core.Data;
using ArcGIS.Core.Geometry;
using ArcGIS.Desktop.Editing;
using ArcGIS.Desktop.Framework.Threading.Tasks;
using ArcGIS.Desktop.Mapping;
using System;
using System.Diagnostics;
using System.Linq;
using System.Threading.Tasks;

namespace ToolTester
{
    internal class MapTool1 : MapTool
    {
        public MapTool1()
        {
            IsSketchTool = true;
            SketchType = SketchGeometryType.Point;
            SketchOutputMode = SketchOutputMode.Map;
        }

        protected override Task OnToolActivateAsync(bool active)
        {
            return base.OnToolActivateAsync(active);
        }

        protected override Task<bool> OnSketchCompleteAsync(Geometry geometry)
        {
            return QueuedTask.Run(() =>
            {
                var fLayer = this.ActiveMapView.GetSelectedLayers().FirstOrDefault() as FeatureLayer;
                //condition="esri_mapping_featureLayerSelectedCondition" in the daml should prevent this ...
                if (fLayer == null)
                    return true;
                //use whatever field is been set as Display Field in the layer properties ...
                var fldName = ((CIMFeatureLayer)fLayer.GetDefinition()).FeatureTable.DisplayField;
                string fileName = GetFirstRow(fLayer, fldName, geometry);
                if (!string.IsNullOrWhiteSpace(fileName))
                {
                    Uri myUri = new Uri($@"C:\Temp\{fileName}.lyrx");
                    Debug.Print(fileName);
                    //todo: verify file exists, layer not already added, etc.
                    //Layer newlayer = LayerFactory.Instance.CreateFeatureLayer(myUri, this.ActiveMapView.Map, LayerPosition.AddToTop);
                }
                return true;
            });
        }
        private string GetFirstRow(FeatureLayer fLayer, string fldName, Geometry geom)
        {
            string s = "";
            GeometryEngine.Instance.Project(geom, fLayer.GetSpatialReference());
            using (var cursor = fLayer.Search(new SpatialQueryFilter()
            {
                FilterGeometry = GeometryEngine.Instance.Project(geom, fLayer.GetSpatialReference()),
                SpatialRelationship = SpatialRelationship.Intersects,
                SubFields = fldName
            }))
            {
                if (cursor.MoveNext())
                    s = cursor.Current[fldName].ToString();
            };
            return s;
        }
    }
}

 

 

JohnHanson1
New Contributor

Mr. Kuykendall,

Perfect!  Thank you very much!  I had added some C# code to add layers from a selection, and it works like a charm.  I attached the modified code of the MapTool1.cs (zipped) below.

Once again, Thank you

John Hanson

0 Kudos