ArcEngine实现捕捉节点

时间:2022-10-29 06:05:26

来自:http://blog.sina.com.cn/s/blog_4d0b75870100o960.html

//获取最近的结点,然后在  OnMouseMove中显示

//pnt:鼠标移动点

//mapSize:设置的地理范围

public static IPoint GetNearestVertex(IActiveView actview, IPoint pnt, double mapSize)
        {
            IPoint vetex = null;
            IPoint hitPnt=new PointClass();
            IHitTest hitTest = null;
            IPointCollection pntColl =new MultipointClass();
            IProximityOperator prox = null;
            double hitdis=0;
            int hitpartindex=0,hitsegindex=0;
            Boolean rside = false;
            IFeatureCache2 featCache = new FeatureCacheClass();
            double pixelSize = ConvertMapUnitsToPixels(actview, mapSize);  //将地理范围转化为像素
            featCache.Initialize(pnt, pixelSize);  //初始化缓存
            for (int i = 0; i < actview.FocusMap.LayerCount; i++)
            {

//只有点、线、面并且可视的图层才加入缓存
                IFeatureLayer featLayer =(IFeatureLayer) actview.FocusMap.get_Layer(i);
                if (featLayer != null && featLayer.Visible == true &&
                    (featLayer.FeatureClass.ShapeType==esriGeometryType.esriGeometryPolyline ||
                    featLayer.FeatureClass.ShapeType == esriGeometryType.esriGeometryPolygon ||
                    featLayer.FeatureClass.ShapeType == esriGeometryType.esriGeometryPoint))
                {
                    featCache.AddFeatures(featLayer.FeatureClass, null);
                    for (int j = 0; j < featCache.Count; j++)
                    {
                        IFeature feat = featCache.get_Feature(j);
                        hitTest =(IHitTest ) feat.Shape;

//捕捉节点,另外可以设置esriGeometryHitPartType,捕捉边线点,中间点等。
                        if (hitTest.HitTest(pnt, mapSize, esriGeometryHitPartType.esriGeometryPartVertex, hitPnt, ref hitdis, ref hitpartindex, ref hitsegindex, ref rside))
                        {
                            object obj=Type.Missing ;
                            pntColl.AddPoint(hitPnt,ref obj,ref obj);
                            break;
                        }
                    }
                }
            }
            prox =(IProximityOperator)pnt;
            double minDis=0, dis=0;
            for (int i = 0; i < pntColl.PointCount; i++)
            {
                IPoint tmpPnt=pntColl.get_Point(i);
                dis= prox.ReturnDistance(tmpPnt);
                if (i == 0)
                {
                    minDis = dis;
                    vetex = tmpPnt;
                }
                else
                {
                    if (dis < minDis)
                    {
                        minDis = dis;
                        vetex = tmpPnt;
                    }
                }
            }
            return vetex;
        }