• AO Identify地图交互


    转自supernever文章 Identify

     

    1、框选要素高亮显示

    private void axMapControl1_OnMouseDown(object sender, ESRI.ArcGIS.Controls.IMapControlEvents2_OnMouseDownEvent e)
            {
                IGeometry pGeo = axMapControl1.TrackRectangle();
                ISpatialFilter pSpatialFilter = new SpatialFilterClass();
                pSpatialFilter.Geometry = pGeo;
                pSpatialFilter.GeometryField = "SHAPE";
                pSpatialFilter.SpatialRel = esriSpatialRelEnum.esriSpatialRelContains;

                IArray geoArray = new ArrayClass();
                IMap pMap = axMapControl1.Map;
               
                for (int i = 0; i < pMap.LayerCount; i++)
                {

                    IFeatureLayer pFeatureLayer = pMap.get_Layer(i) as IFeatureLayer;
                    if(pFeatureLayer.Visible!=true)
                        continue;                
                    IFeatureCursor pFeatureCursor = pFeatureLayer.Search(pSpatialFilter, false);

                    IFeature pFeature = pFeatureCursor.NextFeature();
                    while (pFeature != null)
                    {
                        geoArray.Add(pFeature);
                        pFeature = pFeatureCursor.NextFeature();
                    }
                }
                FlashAndIdentify(geoArray);
            }

            /// <summary>
            /// 对所选择要素集进行高亮显示并打开属性查询窗口
            /// </summary>
            /// <param name="inArray">所选择的要素集</param>
            private void FlashAndIdentify(IArray inArray)
            {
                try
                {
                    if (inArray == null)
                        return;
                    HookHelperClass hookHelper = new HookHelperClass();
                    hookHelper.Hook = axMapControl1.Object;

                    IHookActions hookAction = (IHookActions)hookHelper;                
                    hookAction.DoActionOnMultiple(inArray, esriHookActions.esriHookActionsFlash);
                    
                    frmIdentify newFrm = frmIdentify.CreatIdentify((IHookHelper)hookHelper, inArray);
                    newFrm.Show();
                    newFrm.ShowProperty(inArray);

                }
                catch (Exception exc) { MessageBox.Show(exc.Message); }
            }

    /// <summary>
            /// 打开Identify对话框,并显示所选择的要素集
            /// </summary>
            /// <param name="array">要素集</param>
            public void ShowProperty(IArray array)
            {
                tvFeature.Nodes.Clear();
                lvProperty.Items.Clear();
                int geoCount = array.Count;
                if (geoCount > 0)
                {
                    toolStripStatusLabel1.Text = "共选择" + geoCount + "条记录";
                    for (int count = 0; count < geoCount; count++)
                    {
                        IFeature pFeature = array.get_Element(count) as IFeature;
                        IFields pFields = pFeature.Fields;
                        int FieldIndex = pFields.FindField("OBJECTID");
                        TreeNode newNode = new TreeNode(pFeature.get_Value(FieldIndex).ToString());
                        tvFeature.Nodes.Add(newNode);
                    }

                    IFeature pF = array.get_Element(0) as IFeature;
                    listview = IdentifyFeature.getFeaturePorperty(pF);
                    for (int index = 0; index < listview.Items.Count; index++)
                    {
                        lvProperty.Items.Add(listview.Items[index].Clone() as ListViewItem);//ListViewItem只能添加到一个ListView中,此处使用Clone方法
                    }
                }
                else
                    toolStripStatusLabel1.Text = "共选择0条记录";

            }

    /// <summary>
            /// 高亮显示所点击节点代表的要素及其属性
            /// </summary>
            /// <param name="lvIndex">节点索引</param>
            /// <param name="FeatureArray">所选择的要素集</param>

            private void NodeClicktoFeature(int lvIndex, IArray FeatureArray)
            {
                IFeature pFeature = FeatureArray.get_Element(lvIndex) as IFeature;
                listview = IdentifyFeature.getFeaturePorperty(pFeature);
                lvProperty.Items.Clear();
                for (int index = 0; index < listview.Items.Count; index++)
                {
                    lvProperty.Items.Add(listview.Items[index].Clone() as ListViewItem);//ListViewItem只能添加到一个ListView中,此处使用Clone方法
                }
                IHookActions hookAction = pHookHelper as IHookActions;
                hookAction.DoAction(pFeature.ShapeCopy, esriHookActions.esriHookActionsFlash);
            }

    /// <summary>
            /// 显示每个要素信息
            /// </summary>
            /// <param name="pFeature">选择的要素</param>
            /// <returns></returns>
            public static ListView getFeaturePorperty(IFeature pFeature)
            {
                ListView listview = new ListView();
                listview.View = System.Windows.Forms.View.Details;

                IFields pFields = pFeature.Fields;
                for (int index = 0; index < pFields.FieldCount; index++)
                {
                    string strValue, strField;
                    strField = pFields.get_Field(index).Name.ToString();
                    if (pFields.get_Field(index).Type == esriFieldType.esriFieldTypeGeometry)
                    {
                        strValue = pFeature.Shape.GeometryType.ToString();
                        switch (strValue)
                        {
                            case "esriGeometryPoint":
                                strValue = "点";
                                break;
                            case "esriGeometryPolyline":
                                strValue = "线";
                                break;
                            case "esriGeometryPolygon":
                                strValue = "面";
                                break;
                        }
                    }
                    else
                    {
                        strValue = pFeature.get_Value(index).ToString();
                        if (strValue == "")
                            strValue = "<null>";
                    }
                    ListViewItem item = new ListViewItem();
                    item.SubItems[0].Text = strField;
                    item.SubItems.Add(strValue);
                    listview.Items.Add(item);
                }
                return listview;            
            }



    (四)用AE实现点击查看属性

    关于ARCGISIDENTIFY功能的实现

    一:功能实现的基本思路是这样的:

    1. 点击时,先获取点击位置的屏幕坐标,然后转换到地图坐标;

    2. 定义一个图层对象(Identify),调用相应的Identify方法生成点对象;

    3. 提取图层中点击处的图形,提取属性,填充到事先设计好的窗口中;

    4. 显示窗口。

     

    二:代码

    IIdentify pIdentify;    //IIdentify接口(要素图层下的一个接口)定义了获得要素图层单个要素的属性的捷径方法。它有一Identify方法,返回一个IArray数组对象。

                    IPoint pPoint;

                    IArray pIDArray;

                    IFeatureIdentifyObj pFeatIdObj;//定义一个要素对象

                    IIdentifyObj pIdObj;

                    IMap pMap = axMapControl1.Map;//将当前地图赋给地图对象pMap

                    pIdentify = pMap.get_Layer(0) as IIdentify;//将图层赋给图层对象pIdentify

                    pPoint = new PointClass();//定义了一个实现IPoint接口的点对象

                    pPoint.PutCoords(e.mapX, e.mapY);//pPoint.PutCoords用来设置点的X,Y值从而创建一个点对象。       

                    pPoint.SpatialReference = pMap.SpatialReference;

                    pIDArray = pIdentify.Identify(pPoint);//Identify方法返回一个Array数组对象

     

                    if (pIDArray != null)

                    {

                        pFeatIdObj = pIDArray.get_Element(0) as IFeatureIdentifyObj;//获得要素集数组中的第一个元素

                        pIdObj = pFeatIdObj as IIdentifyObj;

                        pIdObj.Flash(axMapControl1.ActiveView.ScreenDisplay);//选中要素闪烁

                        MessageBox.Show("Layer˖ +  pIdObj.Layer.Name +

                    System.Environment.NewLine + "Feature˖ + pIdObj.Name);//显示要素所在图层的名字,要素的的名字

                    }

                    else

                        MessageBox.Show("没有要素选中");

     

    程序的运行结果如图,说明Identify方法生成的数组为空,如下图;

     

     

    三:程序调试

    问题分析:

    出现上述问题的原因是IPoint没有和图层建立关系,即无论你有没有点到图层中的点,程序都会通过pPoint.PutCoords(e.MapX,e.MapY)生成点对象,但是pIdentify.identify()方法对参数(pPoint)的传递无响应,该方法只会识别图层中的元素,因此返回的数组始终是空NULL;

    问题解决:

    参考AE帮助中的DEMO,在此不用point对象,建立一个Envelop对象pEnv(相当于缓冲区), 将该对象作为参数传递给Identify方法就可以了

    最终运行结果

     

    四:相关理论知识总结

    用到的相关对象 方法 接口:

    IMap接口 是开始多数GIS任务的起点,它主要用于管理Map对象中的layer对象,要素选择集、MapSourround对象、标注引擎和空间参考等对象。IMap接口中定义了大量的方法来操作它其中的图层对象(如:AddLayer ClearLayers)。

    IIdentify接口定义了获得要素图层单个要素的属性的捷径方法。它有一个Identify方法,返回一个IArray数组对象。

    IPoint接口定义了Point对象的属性和方法,ID属性可以返回点队形的ID号。使用IPoint::XIPoint::Y用户可以获得一个点的XY的坐标值。

    IPoint::PutCoords用于设置一个点的XY坐标值,当用户new完成一个Point后,可以用这个方法来建立一个实际的点对象。

    包络线Envelop

    Envelop通过它的最大和最小X,Y坐标来定义一个矩形形状,因此包络线对象相对于它的空间参考而言总是直角的。包络线也定义了最大的和最小的Z值、M值,这两个值分别通过IZAware,IMAware接口来定义。

     

     

    IEnvelope::PutCoords:提供了一种构造了包络线的方法,它通过传入XMinYMinXMax,YMax四个点对象而返回一个包络线;IEnvelop::Query则可以返回一个包络线的四个值。

    五:

    该程序的属性显示用了一个MESSAGEBOX,功能过于简单,没法对元素所有属性字段的显示,需要找一个合适的控件对其属性进行展示。

  • 相关阅读:
    day7django数据库操作
    day4django请求和响应、视图
    计算数字 k 在 0 到 n 中的出现的次数,k 可能是 0~9 的一个值
    day5crm模型、数据库增删改查
    存储过程和自定义函数的区别
    mysql复制表
    搜索关键词高亮
    classpath目录
    nginx 转发https请求
    Bert pretraining
  • 原文地址:https://www.cnblogs.com/arxive/p/6622024.html
Copyright © 2020-2023  润新知