示例#1
0
        public PolylineFeature(PolylineFeature feature)
        {
            m_oStyle = feature.m_oStyle;
            m_oParts = new List<Part>();

            foreach (Part part in feature.m_oParts)
            {
                Part newPart = new Part();
                m_oParts.Add(newPart);
                foreach (DPoint point in part.Points)
                {
                    newPart.Points.Add(new DPoint(point));
                }
            }
        }
示例#2
0
        /// <summary>
        /// Casts a point onto polyline and returns location of its projection.
        /// </summary>
        /// <param name="feature">feature of polyline type</param>
        /// <param name="part">part number to analyse</param>
        /// <param name="x">point being cast x coord</param>
        /// <param name="y">point being cast y coord</param>
        /// <param name="a">normalized cast location along the polyline part [0..1]</param>
        /// <param name="x_cast">cast x location on the polyline</param>
        /// <param name="y_cast">cast y location on the polyline</param>
        /// <param name="dDist">distance of point and polyline</param>
        /// <param name="dPolyLen">calculated polyline length</param>
        /// <param name="segNo">number of polyline segment that was closest (0-based)</param>
        /// <param name="a_seg">normalized position within polyline segment (note that a_seg might be outside of 0..1 range). Value smaller than 0 or greater than 1 denotes, that point is cast to end point of segment.</param>
        /// <param name="b_seg">distance from a line defined by polyline segment. Side is indicated by sign: positive for right side, negative for left side.</param>
        public void castToPolyline(PolylineFeature feature, int part, double x, double y,
            out double a, out double x_cast, out double y_cast,
            out double dDist, out double dPolyLen,
            out int segNo, out double a_seg, out double b_seg)
        {
            if (feature == null) throw new Exception("Invalid parameter: feature can not be null.");

            if (part < 0 || part > feature.m_oParts.Count) throw new Exception("Invalid parameter: part.");

            Part polylinePart = feature.m_oParts[part];

            if (polylinePart.Points.Count == 0)
            {
                dDist = double.MaxValue;
                a = 0;
                x_cast = double.MaxValue;
                y_cast = double.MaxValue;
                dPolyLen = 0;
                segNo = -1;
                a_seg = 1;
                b_seg = 1;
                return;
            }

            double a_tmp, b_tmp;
            double dSegLen;
            double dDistMin = -1;
            double dDistTmp = -1;
            dDist = 0;
            dPolyLen = 0;
            a = 0;
            a_seg = 0;
            b_seg = 0;
            segNo = 0;
            x_cast = 0;
            y_cast = 0;
            for (int j = 1; j < polylinePart.Points.Count; j++)
            {
                double ax, ay, bx, by;
                ax = polylinePart.Points[j - 1].X;
                ay = polylinePart.Points[j - 1].Y;
                bx = polylinePart.Points[j].X;
                by = polylinePart.Points[j].Y;

                dSegLen = Math.Sqrt((ax - bx) * (ax - bx) + (ay - by) * (ay - by));

                if (dSegLen > 0)
                {
                    // a=0..1  -> rzut punktu x jest miedzy poczatkiem i koncem odcinka ab
                    a_tmp = ((x - ax) * (bx - ax) + (y - ay) * (by - ay)) / ((bx - ax) * (bx - ax) + (by - ay) * (by - ay));
                    b_tmp = ((bx - ax) * (ay - y) - (by - ay) * (ax - x)) / dSegLen;
                    if (a_tmp > 0 && a_tmp < 1)
                    {  // policz odleglosc w rzucie do odcinka
                        dDistTmp = Math.Abs(b_tmp);
                    }
                    else if (a_tmp >= 1)
                    {
                        dDistTmp = Math.Sqrt((bx - x) * (bx - x) + (by - y) * (by - y));
                    }
                    else
                    {
                        dDistTmp = Math.Sqrt((ax - x) * (ax - x) + (ay - y) * (ay - y));
                    }
                }
                else
                {
                    // ignore this segment
                    a_tmp = 0;
                    b_tmp = 0;
                    dDistTmp = Math.Sqrt((ax - x) * (ax - x) + (ay - y) * (ay - y));
                }

                if (dDistTmp < dDistMin || dDistMin == -1)
                {
                    a_seg = a_tmp;
                    b_seg = b_tmp;
                    segNo = j - 1;
                    dDist = dDistTmp;
                    dDistMin = dDistTmp;

                    double dA_tmp;
                    dA_tmp = a_seg;
                    if (dA_tmp > 1) dA_tmp = 1;
                    if (dA_tmp < 0) dA_tmp = 0;

                    a = dPolyLen + dA_tmp * dSegLen;
                }
                dPolyLen += dSegLen;
            }

            if (dPolyLen == 0) throw new Exception("Polyline length can not be zero.");
            a = a / dPolyLen;
            {
                double ax, ay, bx, by;
                ax = polylinePart.Points[segNo].X;
                ay = polylinePart.Points[segNo].Y;
                bx = polylinePart.Points[segNo + 1].X;
                by = polylinePart.Points[segNo + 1].Y;
                if (a_seg >= 0 && a_seg <= 1)
                {
                    x_cast = ax + (bx - ax) * a_seg;
                    y_cast = ay + (by - ay) * a_seg;
                }
                else if (a_seg < 0)
                {
                    x_cast = ax;
                    y_cast = ay;
                }
                else if (a_seg > 1)
                {
                    x_cast = bx;
                    y_cast = by;
                }
            }
        }
示例#3
0
 public void recordAddFeature(PolylineFeature feature)
 {
     featuresContainer.addFeature(feature); // make feature attached
     undoElementCurrent.addFeature(feature);
     redoElements.Clear();
 }
示例#4
0
 public void addFeature(PolylineFeature feature)
 {
     UndoElementPrimitive elem = new UndoElementPrimitive();
     elem.featureAdded(feature);
     undoPrimitives.Add(elem);
 }
示例#5
0
 public void featureAdded(PolylineFeature feature)
 {
     operationType = UndoElementType.InsertFeature;
     this.featureIndex = feature.FeatureID;
 }
示例#6
0
        public override void KeyDown(object sender, KeyEventArgs e)
        {
            base.KeyDown(sender, e);
            // delete selected features and points

            if (e.KeyCode == Keys.Delete)
            {
                // delete selected points, split polyline into two where applicable

                // start recording undo step
                polylineLayer.Manager.startRecordingUndoElement();
                symbolLayer.Manager.startRecordingUndoElement();

                int count = polylineLayer.FeaturesCount;
                for (int iFeature = count - 1; iFeature >= 0; iFeature--)
                {
                    Feature feature = polylineLayer.FeatureGet(iFeature);
                    if (feature == null) continue;

                    if (feature.Selected)
                    {
                        // remove this polyliline and all related symbols
                        PolylineFeature poly = (PolylineFeature)feature;
                        for (int iPart = 0; iPart < poly.m_oParts.Count; iPart++)
                        {
                            Part part = poly.m_oParts[iPart];
                            for (int iPoint = 0; iPoint < part.Points.Count; iPoint++)
                            {
                                DPoint point = part.Points[iPoint];
                                symbolLayer.Manager.recordRemoveFeature((SymbolFeature)point.Tag);
                            }
                        }
                        polylineLayer.Manager.recordRemoveFeature((PolylineFeature)feature);
                    }
                    else
                    {
                        // building points of polyline
                        // select polyline points
                        if (feature is PolylineFeature)
                        {
                            PolylineFeature oP = (PolylineFeature)feature;

                            // if this polyline has selected point(s), it will be split
                            // calculate number of new polylines

                            int newPolylines = 0;
                            int partCount = oP.m_oParts.Count;
                            for (int iPart = partCount - 1; iPart >= 0; iPart--)
                            {
                                List<DPoint> points = oP.m_oParts[iPart].Points;
                                int pointCount = points.Count;
                                for (int iPoint = 1; iPoint < pointCount; iPoint++)
                                {
                                    if (iPoint == 1)
                                    {
                                        newPolylines = (points[0].Selected ? 0 : 1);
                                    }

                                    if (points[iPoint - 1].Selected == true
                                        && points[iPoint].Selected == false)
                                    {
                                        newPolylines++;
                                    }
                                }
                            }

                            if (newPolylines < 2)
                            {
                                // just modify existing polyline
                                int partCount1 = oP.m_oParts.Count;
                                for (int iPart = partCount1 - 1; iPart >= 0; iPart--)
                                {
                                    List<DPoint> points = oP.m_oParts[iPart].Points;
                                    int pointCount = points.Count;
                                    for (int iPoint = pointCount - 1; iPoint >= 0; iPoint--)
                                    {
                                        if (points[iPoint].Selected)
                                        {
                                            symbolLayer.Manager.recordRemoveFeature((SymbolFeature)points[iPoint].Tag);
                                            polylineLayer.Manager.recordRemovePoint(iFeature, iPart, iPoint);
                                        }
                                    }
                                    if (points.Count == 0)
                                    {
                                        polylineLayer.Manager.recordRemovePart(iFeature, iPart);
                                    }
                                }
                                if (oP.m_oParts.Count == 0)
                                {
                                    polylineLayer.Manager.recordRemoveFeature((PolylineFeature)feature);
                                }
                            }
                            else
                            {
                                // add new polyline(s), delete original
                                PolylineFeature featureNew = null;
                                List<DPoint> newPoints = null;

                                // draw polyline points
                                int partCount1 = oP.m_oParts.Count;
                                for (int iPart = partCount1 - 1; iPart >= 0; iPart--)
                                {
                                    List<DPoint> points = oP.m_oParts[iPart].Points;
                                    int pointCount = points.Count;
                                    for (int iPoint = 0; iPoint < pointCount; iPoint++)
                                    {
                                        if (points[iPoint].Selected)
                                        {
                                            if (newPoints != null)
                                            {
                                                featureNew = new PolylineFeature(newPoints, feature.Style);
                                                polylineLayer.Manager.recordAddFeature(featureNew);
                                                featureNew = null;
                                                newPoints = null;
                                            }

                                            symbolLayer.Manager.recordRemoveFeature((SymbolFeature)points[iPoint].Tag);
                                        }
                                        else
                                        {
                                            if (newPoints == null) newPoints = new List<DPoint>();
                                            newPoints.Add((DPoint)points[iPoint].Clone());
                                        }
                                    }
                                }

                                if (newPoints != null)
                                {
                                    featureNew = new PolylineFeature(newPoints, feature.Style);
                                    polylineLayer.Manager.recordAddFeature(featureNew);
                                    featureNew = null;
                                    newPoints = null;
                                }

                                polylineLayer.Manager.recordRemoveFeature(feature);
                            }
                        }
                    }
                }

                // finish recording undo step
                polylineLayer.Manager.stopRecordingUndoElement();
                symbolLayer.Manager.stopRecordingUndoElement();

                // emit event
                ToolUsed(this, new EventArgs());
            }
            // clear selection
            MapControl.Globals.Instance.MapControl.InvalidateMap();
        }