コード例 #1
0
        }                                                  // Default constructor

        public CListLines(int maxL2, int maxV, int maxArc) // constructor
        {
            MaxPoly  = maxL2;
            MaxVert  = maxV;
            MaxArc   = maxArc;
            pQ       = new CQue(1000); // necessary to find connected components
            nArc     = 0;
            nPolygon = 0;
            Polygon  = new CPolygon[MaxPoly];
            int i = 0;

            for (i = 0; i < MaxPoly; i++)
            {
                Polygon[i] = new CPolygon();
            }
            Vert = new iVect2[MaxVert];
            for (i = 0; i < MaxVert; i++)
            {
                Vert[i] = new iVect2();
            }
            Arc = new CArc[MaxArc];
            for (i = 0; i < MaxArc; i++)
            {
                Arc[i] = new CArc();
            }
            Arc2 = new CArc2[MaxArc];
            for (i = 0; i < MaxArc; i++)
            {
                Arc2[i] = new CArc2();
            }
            Step = new iVect2[4];
            for (i = 0; i < 4; i++)
            {
                Step[i] = new iVect2();
            }
            Norm = new iVect2[4];
            for (i = 0; i < 4; i++)
            {
                Norm[i] = new iVect2();
            }

            Step[0].X = 1; Step[0].Y = 0;
            Step[1].X = 0; Step[1].Y = 1;
            Step[2].X = -1; Step[2].Y = 0;
            Step[3].X = 0; Step[3].Y = -1;

            Norm[0].X = 0; Norm[0].Y = 1;
            Norm[1].X = -1; Norm[1].Y = 0;
            Norm[2].X = 0; Norm[2].Y = -1;
            Norm[3].X = 1; Norm[3].Y = 0;
        } //*************** end constructor *********************
コード例 #2
0
        } // ********************** end DrawArc *********************************

        public int Curvature(int x1, int y1, int x2, int y2, int x3, int y3,
                             double eps, ref CArc arc)

        /* Calculates the curvature 'k' of an arc lying in the tolerance tube
         * around the given two polygon edges [(x1,y1), (x2,y2)] and
         * [(x2,y2), (x3,y3)] and having the outer boundary of the tube as its
         * tangent. The tangency point should be not farther as the half length
         * of the shorter edge from (x2,y2). The radius of the arc should be as
         * large as possible. */
        {
            //bool deb = false;
            double a1, a2, lp,                                 // Variables for calculating the projections
                   dx1, dy1, dx2, dy2, len1, len2,             // Inkrements, lengths of edges
                   cosgam,                                     // cosine of the outer angle between the edges
                   sinbet, cosbet,                             // cosine and sine of the half angle
                   strip = 0.6,                                // correcture of the deviation
                   k, cru1, cru2;                              // curvature for long and short edges

            dx1  = (double)(x2 - x1); dy1 = (double)(y2 - y1); // first edge
            len1 = Math.Sqrt(dx1 * dx1 + dy1 * dy1);
            dx2  = (double)(x3 - x2); dy2 = (double)(y3 - y2); // second edge
            len2 = Math.Sqrt(dx2 * dx2 + dy2 * dy2);
            if ((len1 == 0.0) || (len2 == 0.0))
            {
                return(-1);
            }

            cosgam = (dx1 * dx2 + dy1 * dy2) / len1 / len2; // angle between the edges
            if (Math.Abs(cosgam) <= 1.0)
            {
                sinbet = Math.Sqrt((1.0 - cosgam) * 0.5);   // half angle
            }
            else
            {
                sinbet = 0.0;
            }
            cosbet = Math.Sqrt((1.0 + cosgam) * 0.5);

            cru1 = (1.0 - cosbet) / (eps - strip); // long edge, it is important
            // that the arc goes throught the vertex
            double min_len = len1;

            if (len2 < min_len)
            {
                min_len = len2;
            }
            if (min_len != 0.0 && cosbet != 0.0)
            {
                cru2 = 2.0 * sinbet / cosbet / min_len; // short edge, it is important
            }
            else
            {
                cru2 = 0.0;                  // that the tangency is in the midle of the shortest edge
            }
            if ((Math.Abs(cru1) > Math.Abs(cru2)) && cru1 != 0.0)
            {
                if (cosbet != 0.0 && cru1 != 0.0)
                {
                    lp = sinbet / cosbet / cru1; // distance of the point of tangency from (x2, y2)
                }
                else
                {
                    lp = 100.0;
                }
                k = cru1; // first curvature
            }
            else
            {
                lp = min_len / 2.0;
                k  = cru2 * 0.95; // second curvature
            }

            if (dx1 * dy2 - dy1 * dx2 > 0.0)
            {
                k = -k;                             // the sign
            }
            // the first edge is devided in relation a1 : a2
            a1 = lp / len1;
            a2 = 1.0 - a1;

            if (k != 0.0)
            {
                arc.rad = 1.0F / (float)k;
            }
            else
            {
                arc.rad = 0.0F;
            }

            arc.xb = (float)(x1 * a1 + x2 * a2); // first tangency (begin of the arc)
            arc.yb = (float)(y1 * a1 + y2 * a2);

            a1     = lp / len2; a2 = 1.0 - a1;
            arc.xe = (float)(x3 * a1 + x2 * a2); // second tangency (end of the arc)
            arc.ye = (float)(y3 * a1 + y2 * a2);

            double AbsR, R, chord_X, chord_Y, Length, Lot_x, Lot_y;

            R    = arc.rad;
            AbsR = R;
            if (R < 0.0)
            {
                AbsR = -R;
            }

            chord_X = arc.xe - arc.xb; chord_Y = arc.ye - arc.yb;       // the chord
            Length  = Math.Sqrt(chord_X * chord_X + chord_Y * chord_Y); // Length of the chord

            if (R < 0.0)                                                // 'Lot' is orthogonal to chord
            {
                Lot_x = chord_Y; Lot_y = -chord_X;
            }
            else
            {
                Lot_x = -chord_Y; Lot_y = chord_X;
            }

            if (2 * AbsR < Length)
            {
                return(-1);
            }
            if (Length < 0.1)
            {
                return(-2);
            }

            double Lot = Math.Sqrt(4 * R * R - Length * Length);

            arc.xm = (float)((arc.xb + arc.xe) / 2 - Lot_x * Lot / 2 / Length);
            arc.ym = (float)((arc.yb + arc.ye) / 2 - Lot_y * Lot / 2 / Length);

            if ((arc.xe == arc.xb) && (arc.ye == arc.yb))
            { // can a closed line of three points exist??
                return(-2);
            }
            return(0);
        } // *********************** end Curvature ******************************************************
コード例 #3
0
        }     //************************* end DrawPolygons *************************

        public int DrawArc(CArc arc, bool DispRad, Form1 fm1, int ip)

        /* Draws an arc with radius arc.rad going through (arc.xb, arc.yb) and (arc.xe, arc.ye)
         * with the scale "fm1.Scale1". Draws also the radii at the ends of the arc if arc.rad < maxRad.
         * Starts at the point (arc.xb, arc.yb) undependently of the tracing direction of the polygon.
         */
        {
            bool   bar_on;
            double AbsR, al, del = 0.1, angle = 0.0, R = 0.0, chord_X, chord_Y, Length, fmag = fm1.Scale1,
                   sin_d, cos_d, x = 0, y = 0, xn = 0, yn = 0, fmx = arc.xm, fmy = arc.ym, Scale1 = fm1.Scale1;
            int maxRad = 200, marginX = fm1.marginX, marginY = fm1.marginY, ixb, iyb, ixe, iye, ixm, iym;
            int penWidth = fm1.WidthG / 800;

            if (penWidth == 0)
            {
                penWidth = 1;
            }
            Pen arcPen     = new Pen(Color.Red, penWidth);
            Pen posLinePen = new Pen(Color.Yellow, penWidth);
            Pen negLinePen = new Pen(Color.Violet, penWidth);

            bar_on = fmag >= 2.0; // switches on the filling of the 3x3 rectangles for points

            R    = arc.rad;
            AbsR = R;
            if (R < 0.0)
            {
                AbsR = -R;
            }

            chord_X = arc.xe - arc.xb;
            chord_Y = arc.ye - arc.yb;                                 // the chord

            Length = Math.Sqrt(chord_X * chord_X + chord_Y * chord_Y); // Length of the chord

            ixb = (int)arc.xb;                                         // marginX + (int)(Scale1 * arc.xb);
            iyb = (int)arc.yb;                                         // marginY + (int)(Scale1 * arc.yb);
            ixe = (int)arc.xe;                                         // marginX + (int)(Scale1 * arc.xe);
            iye = (int)arc.ye;                                         // marginY + (int)(Scale1 * arc.ye);
            ixm = (int)arc.xm;                                         // marginX + (int)(Scale1 * arc.xm);
            iym = (int)arc.ym;                                         // marginY + (int)(Scale1 * arc.ym);

            Pen linePen;                                               // = new System.Drawing.Pen(Color.Blue);

            if (AbsR < maxRad && AbsR > 30.0 && DispRad)               // Radius vectors at the end ppoints of the arc
            {
                if (R > 0)
                {
                    linePen = posLinePen;
                }
                else
                {
                    linePen = negLinePen;
                }

                fm1.g2Bmp.DrawLine(linePen, ixm, iym, ixb, iyb);
                fm1.g2Bmp.DrawLine(linePen, ixm, iym, ixe, iye);
            }

            angle = 2.0 * Math.Asin(Length / 2.0 / AbsR); // angle of the arc

            if (R > 0)
            {
                linePen = new Pen(Color.Red);
            }

            del   = 0.1;
            cos_d = Math.Cos(del); // "del" is the step of the circular moving of the point (x, y)
            if (R < 0.0)
            {
                sin_d = -Math.Sin(del);
            }
            else
            {
                sin_d = Math.Sin(del);
            }

            if (angle < 2.0 * del) // The for-loop with 'al' is not used in this case
            {
                fm1.g2Bmp.DrawLine(arcPen, ixb, iyb, ixe, iye);
                xn = yn = 0;
            }
            else
            {
                x = arc.xb - arc.xm;
                y = arc.yb - arc.ym;
                for (al = 0.0; al < angle; al += del) // Drawing an arc step by step
                {
                    xn = x * cos_d + y * sin_d;
                    yn = -x * sin_d + y * cos_d;

                    fm1.g2Bmp.DrawLine(arcPen, (int)(arc.xm + x + 0.5), (int)(arc.ym + y + 0.5),
                                       (int)(arc.xm + xn + 0.5), (int)(arc.ym + yn + 0.5));
                    x = xn; y = yn;
                }
            }
            if (bar_on)
            {
                Brush     myBrush = new System.Drawing.SolidBrush(Color.Violet);
                int       size    = 4;
                Rectangle rect    = new Rectangle((int)arc.xb, (int)arc.yb, size, size);
                fm1.g2Bmp.FillRectangle(myBrush, rect);
                rect = new Rectangle((int)arc.xe, (int)arc.ye, size, size);
                fm1.g2Bmp.FillRectangle(myBrush, rect);
            }
            fm1.pictureBox2.Image = fm1.BmpPictBox2;
            return(0);
        } // ********************** end DrawArc *********************************
コード例 #4
0
        } // ***************************** end FindArcs **************************************************************

        public void CurvatureNew(int x1, int y1, int x2, int y2, int x3, int y3, double eps, ref CArc arc)
        {
            double chordX, chordY, ortX, ortY, Length, dist, VectProd;

            chordX   = x2 - x1;
            chordY   = y2 - y1;
            Length   = Math.Sqrt(chordX * chordX + chordY * chordY);
            arc.rad  = (float)(Length * Length / eps / 8.0);
            arc.xb   = (float)x1;
            arc.yb   = (float)y1;
            arc.xe   = (float)x2;
            arc.ye   = (float)y2;
            dist     = Math.Sqrt(arc.rad * arc.rad - Length * Length / 4.0);
            VectProd = (x2 - x1) * (y3 - y2) - (x3 - x2) * (y2 - y1);
            if (VectProd < 0)
            {
                ortX = chordY;
                ortY = -chordX;
            }
            else
            {
                ortX = -chordY;
                ortY = chordX;
            }

            arc.xm = (float)((x1 + x2) / 2 + ortX * dist / Length);
            arc.ym = (float)((y1 + y2) / 2 + ortY * dist / Length);
        }
コード例 #5
0
        } // *********************** end Curvature ******************************************************

        public int FindArcs(PictureBox pictureBox, CImage EdgeIm, double eps, Form1 fm1)

        /* The method calculates the parametrs of the arcs contained in
         * the polygons. Fills the array 'Arc[]' of structures "CArc". Shows the contents
         * of this array graphically. */
        {
            bool disp = true;
            int  j, ip, first, last, Len, rv, x1, y1, x2, y2, x3, y3;

            nArc = 0;
            Pen    linePen = new System.Drawing.Pen(Color.LightBlue);
            int    marginX = fm1.marginX;
            int    marginY = fm1.marginY;
            double Scale1  = fm1.Scale1;

            fm1.progressBar1.Value   = 0;
            fm1.progressBar1.Visible = true;
            fm1.progressBar1.Step    = 1;
            int jump, Len1 = nPolygon, nStep = 100;

            if (Len1 > 2 * nStep)
            {
                jump = Len1 / nStep;
            }
            else
            {
                jump = 2;
            }
            for (ip = 0; ip < nPolygon; ip++) // ===========================
            {
                if (ip % jump == jump - 1)
                {
                    fm1.progressBar1.PerformStep();
                }
                int cntArc = 0;
                Polygon[ip].firstArc = -1;
                Polygon[ip].lastArc  = -2;
                first = Polygon[ip].firstVert;
                last  = Polygon[ip].lastVert;

                if (last > first + 1)                             // ------- are there sufficient many vertices?-----------
                {
                    if (disp)                                     // here are three points of a polygon calculated but not drawn
                    {
                        x1 = (int)(Scale1 * Vert[first].X + 0.5); // starting point
                        y1 = (int)(Scale1 * Vert[first].Y + 0.5);
                    }
                    x2 = Vert[first].X;     // will become the first point of the arc
                    y2 = Vert[first].Y;
                    x3 = Vert[first + 1].X; // second point
                    y3 = Vert[first + 1].Y;

                    Polygon[ip].firstArc = nArc;

                    // Points from the second one until the one before the last
                    Len = last - first + 1;
                    for (j = 2; j <= Len; j++) // =============================
                    {
                        x1 = x2; y1 = y2;
                        x2 = x3; y2 = y3;
                        x3 = Vert[first + j % Len].X;
                        y3 = Vert[first + j % Len].Y;

                        CArc arc = new CArc();
                        // 'Curvature' calculates and saves parameters of an arc in 'arc'.
                        rv = Curvature(x1, y1, x2, y2, x3, y3, eps, ref arc);

                        if (rv < 0)
                        {
                            continue;
                        }
                        if (Math.Abs(arc.xb - arc.xe) < 1.0 && Math.Abs(arc.yb - arc.ye) < 1.0 || Math.Abs(arc.rad) < 2.0)
                        {
                            continue;
                        }

                        // The arc is saved in the array "Arc" of arcs:
                        Arc[nArc] = arc;
                        if (cntArc == 0)
                        {
                            Polygon[ip].firstArc = nArc;
                        }

                        cntArc++;
                        nArc++;
                        if (disp) //-------------------------------------------------------------
                        {
                            rv = DrawArc(arc, true, fm1, ip);
                            if (rv < 0)
                            {
                                return(-1);
                            }
                        } //---------------------- end if (disp) ---------------------------------------------------------
                        if (j == Len - 1)
                        {
                            Polygon[ip].lastArc = nArc - 1;
                        }
                    } // ======================= end for (j... =========================================================
                }     // ------------------------- end if (last > first+1 ) -----------------------------------------------
            }         // =========================== end for (ip... ==========================================================
            fm1.pictureBox2.Image    = fm1.BmpPictBox2;
            fm1.progressBar1.Visible = false;
            return(0);
        } // ***************************** end FindArcs **************************************************************