Пример #1
0
        public void AddLocation(PartLocation p, string name)
        {
            var nl = new NamedLocation(p, name);

            nl.PropertyChanged += new System.ComponentModel.PropertyChangedEventHandler(ChildPropertyChangedCallback);
            _locations.Add(nl);
        }
Пример #2
0
 public Thing(PartLocation p, PointMode mode)
 {
     X         = p.X;
     Y         = p.Y;
     A         = p.A;
     pointMode = mode;
 }
Пример #3
0
 public bool CNC_XYA(PartLocation loc)
 {
     if (loc == null)
     {
         return(false);
     }
     return(CNC_XYZA(loc.X, loc.Y, loc.A));
 }
Пример #4
0
        /// <summary>
        /// Returns a new list of points offset by X andd Y
        /// </summary>
        public static List <PartLocation> Offset(List <PartLocation> list, PartLocation offset_by)
        {
            var newlist = new List <PartLocation>(list.Count);

            foreach (var x in list)
            {
                newlist.Add(new PartLocation(x.X + offset_by.X, x.Y + offset_by.Y, x.A + offset_by.A));
            }
            return(newlist);
        }
Пример #5
0
        /// <summary>
        /// The furthest distance a fiducial moved
        /// </summary>
        /// <returns></returns>
        public double MaxFiducialMovement()
        {
            Global.Instance.DisplayText(String.Format("Offset = {0}  Angle = {1}", new PartLocation(Offset) - Global.Instance.Locations.GetLocation("PCB Zero"), Angle), System.Drawing.Color.Purple);
            List <double> distances = new List <double>();

            for (int i = 0; i < source.Count; i++)
            {
                var s = new PartLocation(source[i]);
                var d = new PartLocation(dest[i]);
                var m = Map(source[i]);
                // Global.Instance.DisplayText(String.Format("Source {0}  Dest {1}  Mapped {2}", s, d, m), System.Drawing.Color.Purple);
                distances.Add(Map(source[i]).DistanceTo(dest[i]));
            }
            return(distances.Max());
        }
Пример #6
0
        private bool CNC_MoveIsSafe_m(PartLocation p)
        {
            var m = Global.Instance.Locations.GetLocation("max machine");

            if ((p.X < -3.0) || (p.X > m.X) || (p.Y < -3.0) || (p.Y > m.Y))
            {
                ShowSimpleMessageBox("Attempt to move outside safe limits " + p);
                return(false);
            }
            if (_Zguard && IsNeedleDown())
            {
                //needle is down - instead of bitching, just move it up first
                CNC_Z(0);
            }
            return(true);
        }
        public PartLocation Map2(PartLocation from)
        {
            if (ScaleX == 0 || ScaleY == 0)
            {
                throw new Exception("LeastSquareMapping not intialized");
            }

            var p = new PartLocation(from);

            p.X = (from.X + OffsetX) * ScaleX;
            // Why there's a -1 necessary here is beyond me but it works so
            p.Y = (from.Y + OffsetY) * ScaleY - 1;
            p.Rotate(Rotation_);

            return(p);
        }
Пример #8
0
            public static PartLocation Convert(VideoProcessing videoProcessing, PartLocation p, PointMode fromMode, PointMode toMode)
            {
                Thing t = new Thing(p, fromMode);

                t.videoProcessing = videoProcessing;
                switch (toMode)
                {
                case PointMode.MM: return(t.ToMMResolution().ToPartLocation());

                case PointMode.Raw: return(t.ToRawResolution().ToPartLocation());

                case PointMode.Screen: return(t.ToScreenResolution().ToPartLocation());

                case PointMode.ScreenUnzoomed: return(t.ToScreenUnzoomedResolution().ToPartLocation());
                }
                return(null);
            }
Пример #9
0
        /// <summary>
        /// Map a source point to a destination point based on the calibrated inputs
        /// </summary>
        public PartLocation Map(PartLocation from)
        {
            if (Rotation == null || Offset == null)
            {
                throw new Exception("LeastSquareMapping not intialized");
            }

            var x = from.ToMatrix();
            //var y = Rotation * x + Offset;
            var y = (Rotation * (x - SourceCentroid)) + Offset + SourceCentroid; //shift point to center, apply rotation, then shift to the destination
            var p = new PartLocation(y)
            {
                A = from.A + Angle
            };

            return(p);
        }
Пример #10
0
        public static T GetClosest <T>(List <T> list) where T : Shapes.Thing
        {
            if (list == null)
            {
                return(null);
            }
            list.RemoveAll(x => x == null);
            if (list.Count == 0)
            {
                return(null);
            }
            foreach (var x in list)
            {
                x.ToMMResolution();
            }
            PartLocation centerPoint = new PartLocation(0, 0);

            return(list.Aggregate((c, d) => c.DistanceFrom(centerPoint) < d.DistanceFrom(centerPoint) ? c : d));
        }
Пример #11
0
        public void TakePhotoOfPartAtCurrentLocation(TapeObj t)
        {
            if (t == null)
            {
                return;
            }
            var dir = Global.BaseDirectory + @"\images\";

            Directory.CreateDirectory(dir);

            var size = t.GetComponentSize();

            if (size == null)
            {
                return;
            }
            var s = new PartLocation(size.Width, size.Height);                  //assumes 0 degree rotation

            s = (1.5 * s) / MainForm.cameraView.downVideoProcessing.mmPerPixel; //convert to pixels and ad extra 25%
            s.Rotate(t.PartAngle * Math.PI / 180d);                             //and rotate to final position
            s.X = Math.Abs(s.X);                                                //correct for sign changes
            s.Y = Math.Abs(s.Y);

            MainForm.cameraView.SetDownCameraFunctionSet("ComponentPhoto");
            Global.DoBackgroundWork(); //let new images be processed

            var topleft = MainForm.cameraView.downVideoProcessing.FrameCenter - (.5 * s);
            var rect    = new Rectangle(topleft.ToPoint(), s.ToSize());
            var filter  = new Crop(rect);

            using (var image = MainForm.cameraView.downVideoProcessing.GetMeasurementFrame()) {
                using (var cropped = filter.Apply(image)) {
                    var filename = dir + t.ID.Replace(" ", "_") + ".jpg";
                    if (File.Exists(filename))
                    {
                        File.Delete(filename);
                    }
                    cropped.Save(filename, ImageFormat.Jpeg);
                    t.TemplateFilename = filename;
                }
            }
        }
        public static void DoNeedleErrorMeasurement(VideoProcessing vp)
        {
            var          cnc = Global.Instance.cnc;
            var          originalLocation = cnc.XYALocation;
            PartLocation testLocation     = Global.GoTo("Up Camera");

            cnc.Zdown(Properties.Settings.Default.focus_height, true);

            // setup camera
            vp.SetFunctionsList("Needle");
            vp.s.FindCircles = true;
            vp.s.Draw1mmGrid = true;
            var Needle = Global.Instance.needle;

            List <PartLocation> offsetError = new List <PartLocation>();

            for (int i = 0; i <= 360; i += 45)
            {
                testLocation.A = i;
                var pp = testLocation - Needle.NeedleOffset;

                Needle.Move_m(pp); // move to target
                // mark erro
                var circle = VideoDetection.GetClosestCircle(vp, 10);
                if (circle != null)
                {
                    vp.MarkA.Add(circle.ToScreenResolution().ToPartLocation().ToPointF());

                    circle.ToMMResolution();
                    offsetError.Add(circle.ToPartLocation());
                }
                Thread.Sleep(500); //wait 1 second
            }

            Global.Instance.mainForm.ShowSimpleMessageBox("Upcamera offset Error is " + PartLocation.Average(offsetError) + "\nMax Error is " + PartLocation.MaxValues(offsetError));

            cnc.Zup();
            cnc.CNC_XYA(originalLocation);

            //revert to previous state
            vp.Reset();
        }
Пример #13
0
        public bool Move_m(double X, double Y, double A)
        {
            double dX;
            double dY;

            if (!CorrectedPosition_m(A, out dX, out dY))
            {
                return(false);
            }


            var loc    = new PartLocation(X, Y, A);
            var wobble = new PartLocation(dX, dY, 0);

            var dest = loc - wobble + NeedleOffset;

            MainForm.DisplayText("== NEEDLE ==" + String.Format("pos {0} + offset {1} - wobble {2} = {3}", loc, NeedleOffset, wobble, dest), Color.ForestGreen);

            return(Global.Instance.cnc.CNC_XYA(dest));
        }
Пример #14
0
        private static void DrawArrow(ref Bitmap image, List <Shapes.Arrow> arrows)
        {
            using (Image <Bgr, Byte> img = new Image <Bgr, byte>(image)) {
                for (int j = 0; j < arrows.Count; j++)
                {
                    var arrow  = arrows[j];
                    var length = arrow.Length;
                    var loc    = arrow.ToPartLocation();
                    var p      = new Point[5];
                    int i      = 0;
                    p[i++] = new PartLocation(0, 0).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length, 0).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length * .8f, length * .2f).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length, 0).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length * .8f, length * -.2f).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();

                    img.DrawPolyline(p, false, new Bgr(Color.OrangeRed), 2);
                }
                image = img.ToBitmap();
            }
        }
Пример #15
0
        // Part Orientation = orientation if tape is perfectly oriented the way it is oriented
        // deltaOrientation = how far offf the tape is from it's stated orientation
        public PartLocation GetPartLocation(int componentNumber)
        {
            PartLocation part;

            if (FirstPart != null)
            {
                part = GetPartBasedLocation(componentNumber);
            }
            else
            {
                var offset = new PartLocation(componentNumber * PartPitch + HoleToPartSpacingX, HoleToPartSpacingY);
                // add the vector to the part rotated by the tape orientation
                part = new PartLocation(FirstHole) + offset.Rotate(TapeOrientation.ToRadians());
            }
            // add deviation from expected orientation to part orientation
            var deltaOrientation = tapeOrientation.ToRadians() - OriginalTapeOrientationVector.ToRadians();

            part.A = (OriginalPartOrientationVector.ToRadians() + deltaOrientation) * 180d / Math.PI;

            return(part);
        }
Пример #16
0
        public static PointF[] ToRotatedRectangle(Shapes.Rectangle s)
        {
            s.ToRawResolution();
            PointF[] p = new PointF[5];
            p[0].X = (float)s.Left; p[0].Y = (float)s.Top;
            p[1].X = (float)s.Right; p[1].Y = (float)s.Top;
            p[2].X = (float)s.Right; p[2].Y = (float)s.Bottom;
            p[3].X = (float)s.Left; p[3].Y = (float)s.Bottom;
            p[4].X = (float)s.Left; p[4].Y = (float)s.Top;

            // roate about center
            double       angle  = s.A * Math.PI / 180d;
            PartLocation center = new PartLocation(s);

            for (int i = 0; i < p.Length; i++)
            {
                PartLocation pp = new PartLocation(p[i]) - center; //shift to zero
                pp   = pp.Rotate(angle) + center;
                p[i] = pp.ToPointF();
            }

            return(p);
        }
Пример #17
0
        private void calibrateXYmmRev_m(Button sender)
        {
            PartLocation loc = null;
            switch (calibrateXYmmRevStage) {
                case 0:
                    DialogResult dialogresult = ShowMessageBox("All down camera settings, travel settings and offsets will be reset", "Resetting Data", MessageBoxButtons.OKCancel);
                    if (dialogresult == DialogResult.Cancel) { return; }

                    // Reset all necessary values

                    tr1_textBox.Text = "40";
                    Cnc.CNC_Write_m("{\"1tr\":" + tr1_textBox.Text + "}");
                    Thread.Sleep(50);

                    tr2_textBox.Text = "40";
                    Cnc.CNC_Write_m("{\"2tr\":" + tr2_textBox.Text + "}");
                    Thread.Sleep(50);

                    SquareCorrection_textBox.Text = "0";
                    setting.CNC_SquareCorrection = 0;
                    CNC.SquareCorrection = 0;

                    instructions_label.Text = "Jog the machine to the center and place the measurement papers center dot under the camera";
                    instructions_label.Visible = true;
                    Cnc.CNC_Home_m("Z");
                    sender.Text = "Next";
                    sender.BackColor = Color.Yellow;
                    calibrateXYmmRevStage++;
                    break;
                case 1:
                    if (Cnc.Simulation)
                    {
                        loc = new PartLocation();
                        loc = Cnc.XYLocation;
                    }
                    else
                    {
                        cameraView.SetDownCameraFunctionSet("homing");
                        cameraView.downSettings.FindCircles = true;
                    retryMidpoint:
                        loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 2, .1);
                        if (loc == null)
                        {
                            ShowSimpleMessageBox("Error, middle point not found - try again");
                            return;
                        }
                        else
                        {
                            if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                                MessageBoxButtons.YesNo) == DialogResult.No) { goto retryMidpoint; }
                        }
                    }
                    calibrateAllStartingPoint = loc;
                    Cnc.CNC_XY(loc.X + 175, loc.Y);

                    instructions_label.Text = "Jog camera to the right edge of the circle only using the X axis";
                    calibrateXYmmRevStage++;
                    break;
                case 2:
                    if (Cnc.XYLocation.Y != calibrateAllStartingPoint.Y ||
                        Cnc.XYLocation.X < calibrateAllStartingPoint.X)
                    {
                        ShowSimpleMessageBox("Y axis moved or X axis more negative than starting point - try again");
                        Cnc.CNC_XY(loc.X + 175, loc.Y);
                        return;
                    }

                    calibrateAllEdgeX = Cnc.XYLocation;
                    Cnc.CNC_XY(calibrateAllStartingPoint.X, calibrateAllStartingPoint.Y + 175);

                    instructions_label.Text = "Jog camera to the top edge of the circle only using the Y axis";
                    calibrateXYmmRevStage++;
                    break;
                case 3:
                    if (Cnc.XYLocation.X != calibrateAllStartingPoint.X ||
                        Cnc.XYLocation.Y < calibrateAllStartingPoint.Y)
                    {
                        ShowSimpleMessageBox("X axis moved or Y axis more negative than starting point - try again");
                        Cnc.CNC_XY(calibrateAllStartingPoint.X, calibrateAllStartingPoint.Y + 175);
                        return;
                    }
                    calibrateAllEdgeY = Cnc.XYLocation;

                    double xStep, yStep;
                    xStep = calibrateAllEdgeX.X / (calibrateAllStartingPoint.X + 175) * 40;
                    yStep = calibrateAllEdgeY.Y / (calibrateAllStartingPoint.Y + 175) * 40;

                    instructions_label.Text = "The calculated xStep is " + Math.Round(xStep, 2).ToString() +
                        " mm/rev, the calculated Y step is " + Math.Round(yStep, 2).ToString() +
                        " mm/rev";

                    tr1_textBox.Text = xStep.ToString();
                    Cnc.CNC_Write_m("{\"1tr\":" + tr1_textBox.Text + "}");
                    Thread.Sleep(50);

                    tr2_textBox.Text = yStep.ToString();
                    Cnc.CNC_Write_m("{\"2tr\":" + tr2_textBox.Text + "}");
                    Thread.Sleep(50);
                    calibrateXYmmRevStage = 0;
                    break;

            }
        }
Пример #18
0
        public void Recomputer3()
        {
            // calculate centroids
            int fiducialCount = 0;

            List<PartLocation> sourceFiducials = new List<PartLocation>();
            List<PartLocation> destFiducials = new List<PartLocation>();

            PartLocation tempDest;

            foreach (var fiducial in source.Where(part => part.physicalComponent.IsFiducial).ToArray())
            {
                sourceCentroidX += fiducial.physicalComponent.X_nominal;
                sourceCentroidY += fiducial.physicalComponent.Y_nominal;
                sourceFiducials.Add(fiducial);

                tempDest = dest[source.IndexOf(fiducial)];

                if (tempDest.physicalComponent != null) {
                    destCentroidX += tempDest.physicalComponent.X_machine;
                    destCentroidY += tempDest.physicalComponent.Y_machine;
                } else {
                    destCentroidX += tempDest.X;
                    destCentroidY += tempDest.Y;
                }
                destFiducials.Add(tempDest);

                fiducialCount++;
            }
            sourceCentroidX /= fiducialCount;
            sourceCentroidY /= fiducialCount;

            destCentroidX /= fiducialCount;
            destCentroidY /= fiducialCount;

            OffsetX = -sourceCentroidX + destCentroidX;
            OffsetY = -sourceCentroidY + destCentroidY;

            List <double> destRotation = new List<double>();
            List <double> sourceRotation = new List<double>();
            List <double> destOffset = new List<double>();
            List <double> sourceOffset = new List<double>();
            List <double> scale = new List<double>();
            List<double> rotationOffset = new List<double>();

            ScaleX = 0; ScaleY = 0; Rotation_ = 0;

            // Calculate offsets from centroids, rotation from source to destination and scale difference
            PartLocation sourceFiducial = null, destFiducial = null;
            for (int i=0; i<fiducialCount; i++) {
                sourceFiducial = sourceFiducials.ElementAt(i);
                destFiducial = destFiducials.ElementAt(i);
                /*
                sourceOffset.Add(Math.Sqrt(Math.Pow(sourceFiducial.X -
                    sourceCentroidX, 2) + Math.Pow(sourceFiducial.Y -
                    sourceCentroidY, 2)));
                destOffset.Add(Math.Sqrt(Math.Pow(destFiducial.X -
                    destCentroidX, 2) + Math.Pow(destFiducial.Y -
                    destCentroidY, 2)));
                 */
                /*
                sourceRotation.Add(Math.Asin((sourceFiducial.Y - sourceCentroidY) /
                    sourceOffset[i]));
                if ((sourceFiducial.X - sourceCentroidX) < 0) {
                    sourceRotation[i] = Math.PI - sourceRotation[i]; }
                if (sourceRotation[i] < 0) { sourceRotation[i] += Math.PI * 2; }

                destRotation.Add(Math.Asin((destFiducial.Y - destCentroidY) /
                    destOffset[i]));
                if ((destFiducial.X - destCentroidX) < 0) {
                    destRotation[i] = Math.PI - destRotation[i]; }
                if (destRotation[i] < 0) { destRotation[i] += Math.PI * 2; }
                */
                sourceRotation.Add(Math.Atan2(sourceFiducial.Y - sourceCentroidY,
                    sourceFiducial.X - sourceCentroidX));
                destRotation.Add(Math.Atan2(destFiducial.Y - destCentroidY,
                    destFiducial.X - destCentroidX));

                rotationOffset.Add(destRotation[i] - sourceRotation[i]);

                //scale.Add(destOffset[i] / sourceOffset[i]);

                Rotation_ += rotationOffset[i];
                ScaleX += (destFiducial.X - destCentroidX) / (sourceFiducial.X - sourceCentroidX);
                ScaleY += (destFiducial.Y - destCentroidY) / (sourceFiducial.Y - sourceCentroidY);
            }

            Rotation_ /= fiducialCount;
            ScaleX /= fiducialCount;
            ScaleY /= fiducialCount;

            var p = new PartLocation();
            double xFid, yFid;
            foreach (PartLocation fiducial in sourceFiducials)
            {
                p.X = (fiducial.X - sourceCentroidX) * ScaleX;
                p.Y = (fiducial.Y - sourceCentroidY) * ScaleY;
                p.Rotate(Rotation_);
                p.X += sourceCentroidX + OffsetX;
                p.Y += sourceCentroidY + OffsetY;
            }
        }
Пример #19
0
 public PartLocation(PartLocation p)
 {
     X = p.X; Y = p.Y; A = p.A;
 }
Пример #20
0
 public Thing AddOffset(PartLocation p)
 {
     X += p.X; Y += p.Y; A += p.A;
     return(this);
 }
Пример #21
0
        public static PointF[] ToRotatedRectangle(Shapes.Rectangle s)
        {
            s.ToRawResolution();
            PointF[] p = new PointF[5];
            p[0].X = (float)s.Left; p[0].Y = (float)s.Top;
            p[1].X = (float)s.Right; p[1].Y = (float)s.Top;
            p[2].X = (float)s.Right; p[2].Y = (float)s.Bottom;
            p[3].X = (float)s.Left; p[3].Y = (float)s.Bottom;
            p[4].X = (float)s.Left; p[4].Y = (float)s.Top;

            // roate about center
            double angle = s.A * Math.PI / 180d;
            PartLocation center = new PartLocation(s);
            for (int i = 0; i < p.Length; i++) {
                PartLocation pp = new PartLocation(p[i]) - center; //shift to zero
                pp = pp.Rotate(angle) + center;
                p[i] = pp.ToPointF();
            }

            return p;
        }
Пример #22
0
 public PartLocation SetTo(PartLocation p)
 {
     X = p.X; Y = p.Y; A = p.A; return(this);
 }
Пример #23
0
 public Rectangle(PartLocation p, Size s) : base(p.X, p.Y)
 {
     Height = s.Height; Width = s.Width;
 }
Пример #24
0
 public PartLocation OffsetBy(PartLocation p)
 {
     X += p.X; Y += p.Y; A += p.A; return this;
 }
Пример #25
0
 public PartLocation SetTo(PartLocation p)
 {
     X = p.X; Y = p.Y; A = p.A; return this;
 }
Пример #26
0
 /// <summary>
 /// Returns a new list of points offset by X andd Y
 /// </summary>
 public static List<PartLocation> Offset(List<PartLocation> list, PartLocation offset_by)
 {
     var newlist = new List<PartLocation>(list.Count);
     foreach (var x in list) {
         newlist.Add(new PartLocation(x.X + offset_by.X, x.Y + offset_by.Y, x.A + offset_by.A));
     }
     return newlist;
 }
Пример #27
0
 public double DistanceTo(PartLocation p)
 {
     return Math.Sqrt(Math.Pow(X - p.X, 2) + Math.Pow(Y - p.Y, 2));
 }
Пример #28
0
 /*------------ STATIC METHODS ------------------*/
 public static double MeasureSlope(PartLocation[] list)
 {
     // Fit  to linear regression // y:x->a+b*x
     Double[] Xs = list.Select(xx => xx.X).ToArray();
     Double[] Ys = list.Select(xx => xx.Y).ToArray();
     Tuple<double, double> result = SimpleRegression.Fit(Xs, Ys);
     //x.a = result.Item1; //this should be as close to zero as possible if things worked correctly
     return result.Item2; //this represents the slope of the tape
 }
Пример #29
0
 public PartLocation OffsetBy(PartLocation p)
 {
     X += p.X; Y += p.Y; A += p.A; return(this);
 }
Пример #30
0
 public NamedLocation(PartLocation p, string name) : base(p)
 {
     Name = name;
 }
Пример #31
0
        private void calibrateXYZcompensation()
        {
            PartLocation loc = null;
retryAll:
            cameraView.SetDownCameraFunctionSet("");

            ZCorrectionX.Text = "0";
            ZCorrectionY.Text = "0";
            ZCorrectionDeltaZ.Text = "0";
            UpdateZCorrection();

            instructions_label.Text = "Calibrating Z dependent X/Y offset";

            Cnc.CNC_Z(0);
            Cnc.CNC_XY(calibrateAllStartingPoint);

            if (!Cnc.Simulation)
            {
                cameraView.SetDownCameraFunctionSet("homing");
                cameraView.downSettings.FindCircles = true;
            retryMidPoint:
                loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 2, .1);
                if (loc == null)
                {
                    ShowSimpleMessageBox("Error, middle point not found - try again");
                    return;
                }
                if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                    MessageBoxButtons.YesNo) == DialogResult.No) { goto retryMidPoint; }

                calibrateAllStartingPoint = new PartLocation();
                calibrateAllStartingPoint.X = Cnc.TrueX;
                calibrateAllStartingPoint.Y = Cnc.CurrentY;
            }


            Cnc.CNC_Z(Properties.Settings.Default.ZDistanceToTable -
                Properties.Settings.Default.General_ProbingBackOff);
            Cnc.ZGuardOff();

            if (Cnc.Simulation)
            {
                loc = new PartLocation();
                loc.X = calibrateAllStartingPoint.X + 1;
                loc.Y = calibrateAllStartingPoint.Y - 1;
            }
            else
            {
                cameraView.SetDownCameraFunctionSet("homing");
                cameraView.downSettings.FindCircles = true;
            retryMidPointAgain:
                for (int i = 0; i < 8; i++)
                {
                    loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 1.5, .05);
                    if (loc != null) break;
                }
                if (loc == null)
                {
                    ShowSimpleMessageBox("Error, middle point not found - try again");
                    return;
                }
                if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                    MessageBoxButtons.YesNo) == DialogResult.No) { goto retryMidPointAgain; }
                Cnc.ZGuardOn();
            }

            ZCorrectionX.Text = (Cnc.TrueX - calibrateAllStartingPoint.X).ToString();

            ZCorrectionY.Text = (Cnc.CurrentY - calibrateAllStartingPoint.Y).ToString();

            ZCorrectionDeltaZ.Text = (Properties.Settings.Default.ZDistanceToTable -
                Properties.Settings.Default.General_ProbingBackOff).ToString();
            UpdateZCorrection();

            Cnc.CNC_Z(0);
            instructions_label.Text = "";
            instructions_label.Visible = false;

            if (!Cnc.Simulation)
            {
                cameraView.SetDownCameraFunctionSet("homing");
                cameraView.downSettings.FindCircles = true;
            retryMidPoint3:
                loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 2, .1);
                if (loc == null)
                {
                    ShowSimpleMessageBox("Error, middle point not found - try again");
                    return;
                }
                if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                    MessageBoxButtons.YesNo) == DialogResult.No) { goto retryMidPoint3; }
                calibrateAllStartingPoint = loc;
            }
            setNeedleAtCameraPosition();
            Cnc.CNC_Z(Properties.Settings.Default.ZDistanceToTable -
                Properties.Settings.Default.General_ProbingBackOff);
            if (cameraView.ShowMessageBox("Please verify touchdown point. Is point found correctly?", "verification",
                MessageBoxButtons.YesNo) == DialogResult.No) { goto retryAll; }
            Cnc.CNC_Z(0);
        }
Пример #32
0
 public PartLocation(PartLocation p)
 {
     X = p.X; Y = p.Y; A = p.A;
 }
        public PartLocation Map2(PartLocation from)
        {
            if (ScaleX == 0 || ScaleY == 0) throw new Exception("LeastSquareMapping not intialized");

            var p = new PartLocation(from);

            p.X = (from.X + OffsetX) * ScaleX;
            // Why there's a -1 necessary here is beyond me but it works so
            p.Y = (from.Y + OffsetY) * ScaleY - 1;
            p.Rotate(Rotation_);

            return p;
        }
Пример #34
0
 public bool Move_m(PartLocation p)
 {
     return(Move_m(p.X, p.Y, p.A));
 }
Пример #35
0
 public Rectangle(PartLocation p) : base(p.X, p.Y)
 {
 }
Пример #36
0
        public bool PopulateAvailableParts(TapeObj x)
        {
            if (x.FirstHole == null) return false; // currently only handling hole-calibrated harts
            MainForm.Cnc.SlackCompensation = false;
            SetCurrentTapeMeasurement(x.TapeType);

            //find out the max number of parts
            int i = 0;
            PartLocation loc;
            PartLocation addloc = new PartLocation(x.HoleToPartSpacingX, x.HoleToPartSpacingY).Rotate(x.TapeOrientation.ToRadians());

            x.AvailableParts.Clear();
            while (true) {
                loc = x.GetHoleLocation(i);
                if (!MainForm.Cnc.CNC_XY(loc)) { MainForm.Cnc.SlackCompensation = true; return false; }
                var thing = VideoDetection.FindClosest(MainForm.cameraView.downVideoProcessing, Shapes.ShapeTypes.Circle, 1, 3);
                if (thing == null) break;

                if (x.TemplateFilename == null || !File.Exists(x.TemplateFilename))
                {
                    loc += addloc;
                    x.AvailableParts.Add(new NamedLocation(loc, i.ToString()));
                    Global.Instance.mainForm.DisplayText("Adding part "+ i.ToString() +" to "+x.ID);
                }

                if (Cnc.AbortPlacement) { MainForm.Cnc.SlackCompensation = true; return false; }
                i++;
            }
            if (x.TemplateFilename == null || !File.Exists(x.TemplateFilename) && i>0) return true;

            MainForm.cameraView.SetDownCameraFunctionSet("ComponentPhoto");

            double len = i * x.HolePitch;
            double max_components = len / x.PartPitch + 2;
            var list = x.AvailableParts;
            list.Clear();
            if (!MainForm.Cnc.CNC_XY(x.GetPartLocation(0))) { MainForm.Cnc.SlackCompensation = true; return false; } //start off with first part
            for (i = 0; i < max_components; i++) {
                if (Cnc.AbortPlacement) { MainForm.Cnc.SlackCompensation = true; return false; }
                var location = MainForm.FindPositionAndMoveToClosest(Shapes.ShapeTypes.Fiducial, 1, .1, x.TemplateFilename, .5);
                if (location != null) {
                    list.Add(new NamedLocation(location, i.ToString()));
                    if (!MainForm.Cnc.CNC_XY(location + new PartLocation(x.PartPitch, 0).Rotate(x.TapeAngle * Math.PI / 180))) {
                        MainForm.Cnc.SlackCompensation = true;
                        return false;
                    }
                } else {
                    if (!MainForm.Cnc.CNC_XY(Cnc.XYLocation + new PartLocation(x.PartPitch, 0).Rotate(x.TapeAngle * Math.PI / 180))) {
                        MainForm.Cnc.SlackCompensation = true;
                        return false;
                    }
                }
            }
            Global.Instance.mainForm.DisplayText("Detected "+list.Count+" parts for "+x.ID+" ("+String.Join(" ",list)+")");
            MainForm.Cnc.SlackCompensation = true;
            return true;
        }
Пример #37
0
 public Arrow(PartLocation pl, double length) : base(pl, PointMode.Screen)
 {
     Length = length;
 }
Пример #38
0
 public bool Move_m(PartLocation p)
 {
     return Move_m(p.X, p.Y, p.A);
 }
Пример #39
0
        private static void DrawArrow(ref Bitmap image, List<Shapes.Arrow> arrows)
        {
            using (Image<Bgr, Byte> img = new Image<Bgr, byte>(image)) {
                for (int j = 0; j < arrows.Count; j++) {
                    var arrow = arrows[j];
                    var length = arrow.Length;
                    var loc = arrow.ToPartLocation();
                    var p = new Point[5];
                    int i = 0;
                    p[i++] = new PartLocation(0, 0).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length, 0).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length * .8f, length * .2f).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length, 0).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();
                    p[i++] = new PartLocation(length * .8f, length * -.2f).RotateDegrees(loc.A).FlipY().OffsetBy(loc).ToPoint();

                    img.DrawPolyline(p, false, new Bgr(Color.OrangeRed), 2);
                }
                image = img.ToBitmap();
            }
        }
Пример #40
0
        public PartLocation Map2(PartLocation from)
        {
            if (ScaleX == 0 || ScaleY == 0) throw new Exception("LeastSquareMapping not intialized");

            var p = new PartLocation(from);

            //(Rotation * (x - SourceCentroid)) + Offset + SourceCentroid;
            /*
            p.X = (from.X + OffsetX) * ScaleX; // -0.5;
            p.Y = (from.Y + OffsetY) * ScaleY; // -1;
            p.Rotate(Rotation_);
            */
            p.X = (from.X - sourceCentroidX) * ScaleX;
            p.Y = (from.Y - sourceCentroidY) * ScaleY;
            p.Rotate(Rotation_);
            p.X += sourceCentroidX + OffsetX;
            p.Y += sourceCentroidY + OffsetY;

            // double check this
            p.A = from.A + Angle;

            return p;
        }
Пример #41
0
 public NamedLocation(PartLocation p, string name)
     : base(p)
 {
     Name = name;
 }
        private static PartLocation DoCameraCalibration(VideoProcessing vp, PartLocation movement)
        {
            var cnc      = Global.Instance.cnc;
            var distance = new List <PartLocation>();
            var pixels   = new List <PartLocation>();

            // turn on slack compensation
            var savedSlackCompensation = cnc.SlackCompensation;

            cnc.SlackCompensation = true;

            var startingPos = cnc.XYLocation;

            startingPos.A = 0;

            vp.MarkA.Clear();

            for (int i = -4; i < 5; i++)
            {
                //move
                var newLocation = startingPos + (i * movement);
                if (!cnc.CNC_XYA(newLocation))
                {
                    return(null);
                }

                //try 5 times to find a circle
                List <Shapes.Circle> circles = new List <Shapes.Circle>();
                for (int tries = 5; tries > 0 && circles.Count == 0; tries--)
                {
                    circles = VideoDetection.FindCircles(vp);
                }
                if (circles.Count == 0)
                {
                    continue;                     //not found, move and try again
                }
                //find largest circle of the bunch
                var circle = circles.Aggregate((c, d) => c.Radius > d.Radius ? c : d); //find largest circle if we have multiple
                //  var circlePL = (1 / zoom) * circle.ToPartLocation(); //compensate for zoom
                circle.ToScreenUnzoomedResolution();
                distance.Add(newLocation);
                pixels.Add(circle.ToPartLocation());

                vp.MarkA.Add(circle.Clone().ToScreenResolution().ToPartLocation().ToPointF());
                //DisplayText(String.Format("Actual Loc = {0}\t Measured Loc = {1}", newLocation, UpCamera.PixelsToActualLocation(circlePL)), Color.Blue);
            }


            double XmmPerPixel = 0, YmmPerPixel = 0;

            if (pixels.Count < 2)
            {
                Global.Instance.mainForm.ShowMessageBox("Unable To Detect Circles",
                                                        "Try to adjust upcamera processing to see circles, and ensure upcamera needle position is correctly configured",
                                                        MessageBoxButtons.OK);
            }
            else
            {
                // Do regression on X and Y
                var Xs     = pixels.Select(xx => xx.X).ToArray();
                var Ys     = distance.Select(xx => xx.X).ToArray();
                var result = SimpleRegression.Fit(Xs, Ys);
                XmmPerPixel = result.Item2;

                Xs          = pixels.Select(xx => xx.Y).ToArray();
                Ys          = distance.Select(xx => xx.Y).ToArray();
                result      = SimpleRegression.Fit(Xs, Ys);
                YmmPerPixel = result.Item2;


                Global.Instance.DisplayText(String.Format("{0} Xmm/pixel   {1} Ymm/pixel", XmmPerPixel, YmmPerPixel), Color.Purple);

                // Now move to the center

                /* need to get gotolocation upcamera working still
                 * double X, Y; //error offset
                 * GotoUpCamPosition_button_Click(null, null);
                 * for (int tries = 5; tries > 0; tries--) {
                 *   if (GoToLocation_m(UpCamera, Shapes.ShapeTypes.Circle, 1.8, 0.5, out X, out Y)) {
                 *       Properties.Settings.Default.UpCam_PositionX = Cnc.CurrentX + X;
                 *       Properties.Settings.Default.UpCam_PositionY = Cnc.CurrentY - Y;
                 *       UpcamPositionX_textBox.Text = Properties.Settings.Default.UpCam_PositionX.ToString("0.00", CultureInfo.InvariantCulture);
                 *       UpcamPositionY_textBox.Text = Properties.Settings.Default.UpCam_PositionY.ToString("0.00", CultureInfo.InvariantCulture);
                 *
                 *   }
                 * }
                 */
            }

            //restore settings
            cnc.SlackCompensation = savedSlackCompensation;
            vp.MarkA.Clear();
            //return value
            return((pixels.Count < 2) ? null : new PartLocation(Math.Abs(XmmPerPixel), Math.Abs(YmmPerPixel)));
        }
Пример #43
0
        private static PartLocation DoCameraCalibration(VideoProcessing vp, PartLocation movement)
        {
            var cnc = Global.Instance.cnc;
            var distance = new List<PartLocation>();
            var pixels = new List<PartLocation>();

            // turn on slack compensation
            var savedSlackCompensation = cnc.SlackCompensation;
            cnc.SlackCompensation = true;

            var startingPos = cnc.XYLocation;
            startingPos.A = 0;

            vp.MarkA.Clear();

            for (int i = -4; i < 5; i++) {
                //move
                var newLocation = startingPos + (i * movement);
                if (!cnc.CNC_XYA(newLocation)) return null;

                //try 5 times to find a circle
                List<Shapes.Circle> circles = new List<Shapes.Circle>();
                for (int tries = 5; tries > 0 && circles.Count == 0; tries--)
                    circles = VideoDetection.FindCircles(vp);
                if (circles.Count == 0) continue; //not found, move and try again

                //find largest circle of the bunch
                var circle = circles.Aggregate((c, d) => c.Radius > d.Radius ? c : d); //find largest circle if we have multiple
                //  var circlePL = (1 / zoom) * circle.ToPartLocation(); //compensate for zoom
                circle.ToScreenUnzoomedResolution();
                distance.Add(newLocation);
                pixels.Add(circle.ToPartLocation());

                vp.MarkA.Add(circle.Clone().ToScreenResolution().ToPartLocation().ToPointF());
                //DisplayText(String.Format("Actual Loc = {0}\t Measured Loc = {1}", newLocation, UpCamera.PixelsToActualLocation(circlePL)), Color.Blue);
            }

            double XmmPerPixel = 0, YmmPerPixel = 0;
            if (pixels.Count < 2) {
                Global.Instance.mainForm.ShowMessageBox("Unable To Detect Circles",
                    "Try to adjust upcamera processing to see circles, and ensure upcamera needle position is correctly configured",
                    MessageBoxButtons.OK);
            } else {
                // Do regression on X and Y
                var Xs = pixels.Select(xx => xx.X).ToArray();
                var Ys = distance.Select(xx => xx.X).ToArray();
                var result = SimpleRegression.Fit(Xs, Ys);
                XmmPerPixel = result.Item2;

                Xs = pixels.Select(xx => xx.Y).ToArray();
                Ys = distance.Select(xx => xx.Y).ToArray();
                result = SimpleRegression.Fit(Xs, Ys);
                YmmPerPixel = result.Item2;

                Global.Instance.DisplayText(String.Format("{0} Xmm/pixel   {1} Ymm/pixel", XmmPerPixel, YmmPerPixel), Color.Purple);

                // Now move to the center
                /* need to get gotolocation upcamera working still
                 double X, Y; //error offset
                 GotoUpCamPosition_button_Click(null, null);
                 for (int tries = 5; tries > 0; tries--) {
                     if (GoToLocation_m(UpCamera, Shapes.ShapeTypes.Circle, 1.8, 0.5, out X, out Y)) {
                         Properties.Settings.Default.UpCam_PositionX = Cnc.CurrentX + X;
                         Properties.Settings.Default.UpCam_PositionY = Cnc.CurrentY - Y;
                         UpcamPositionX_textBox.Text = Properties.Settings.Default.UpCam_PositionX.ToString("0.00", CultureInfo.InvariantCulture);
                         UpcamPositionY_textBox.Text = Properties.Settings.Default.UpCam_PositionY.ToString("0.00", CultureInfo.InvariantCulture);

                     }
                 }
                 */

            }

            //restore settings
            cnc.SlackCompensation = savedSlackCompensation;
            vp.MarkA.Clear();
            //return value
            return (pixels.Count < 2) ? null : new PartLocation(Math.Abs(XmmPerPixel), Math.Abs(YmmPerPixel));
        }
Пример #44
0
 public void AddLocation(PartLocation p, string name)
 {
     var nl = new NamedLocation(p, name);
     nl.PropertyChanged += new System.ComponentModel.PropertyChangedEventHandler(ChildPropertyChangedCallback);
     _locations.Add(nl);
 }
Пример #45
0
        public void TakePhotoOfPartAtCurrentLocation(TapeObj t)
        {
            if (t == null) return;
            var dir = Global.BaseDirectory + @"\images\";
            Directory.CreateDirectory(dir);

            var size = t.GetComponentSize();
            if (size == null) return;
            var s = new PartLocation(size.Width, size.Height); //assumes 0 degree rotation
            s = (1.5 * s) / MainForm.cameraView.downVideoProcessing.mmPerPixel; //convert to pixels and ad extra 25%
            s.Rotate(t.PartAngle * Math.PI / 180d); //and rotate to final position
            s.X = Math.Abs(s.X); //correct for sign changes
            s.Y = Math.Abs(s.Y);

            MainForm.cameraView.SetDownCameraFunctionSet("ComponentPhoto");
            Global.DoBackgroundWork(); //let new images be processed

            var topleft = MainForm.cameraView.downVideoProcessing.FrameCenter - (.5 * s);
            var rect = new Rectangle(topleft.ToPoint(), s.ToSize());
            var filter = new Crop(rect);

            using (var image = MainForm.cameraView.downVideoProcessing.GetMeasurementFrame()) {
                using (var cropped = filter.Apply(image)) {
                    var filename = dir + t.ID.Replace(" ", "_") + ".jpg";
                    if (File.Exists(filename)) File.Delete(filename);
                    cropped.Save(filename, ImageFormat.Jpeg);
                    t.TemplateFilename = filename;
                }
            }
        }
Пример #46
0
        public PartLocation GetNextComponentPartLocation(TapeObj tapeObj)
        {
            if (tapeObj == null)
            {
                return(null);
            }
            MainForm.DisplayText("GotoNextPart_m(), tape id: " + tapeObj.ID);

            //Load & Parse Data
            if (!tapeObj.IsFullyCalibrated)
            {
                MainForm.ShowSimpleMessageBox("Tape " + tapeObj.ID + " is not yet calibrated.  Please do so and retry");
                return(null);
            }

            PartLocation targetLocation = tapeObj.GetCurrentPartLocation();

            MainForm.DisplayText("Part " + tapeObj.CurrentPartIndex() + "  Source Location = " + targetLocation, Color.Blue);

            // see if part exists for part based detection
            if (tapeObj.TemplateBased)
            {
                Global.Instance.mainForm.cameraView.DownCameraReset();
                if (!MainForm.Cnc.CNC_XY(targetLocation))
                {
                    return(null);
                }
                var thing = MainForm.GoToClosestThing(Shapes.ShapeTypes.Fiducial, 1, .2, null, tapeObj.TemplateFilename, .75);
                if (thing == null)
                {
                    MainForm.DisplayText("No Part Detected At This Location", Color.Red);
                    return(null);
                }
                MainForm.DisplayText("Part Detected : " + thing);
            }


            if (tapeObj.IsLocationBased)
            {
                targetLocation = GetLocationBasedComponent(tapeObj);
            }
            else
            // enhanced part detection
            if (tapeObj.FirstHole != null)
            {
                SetCurrentTapeMeasurement(tapeObj.TapeType);
                Cnc.CNC_XY(tapeObj.GetNearestCurrentPartHole());
                var hole = MainForm.GoToClosestThing(Shapes.ShapeTypes.Circle, 1.5, .1);
                if (hole == null)
                {
                    MainForm.DisplayText("Unable to detect part hole, aborting");
                    return(null);
                }
                var offset = tapeObj.GetCurrentPartLocation() - tapeObj.GetNearestCurrentPartHole();
                targetLocation = hole.ToPartLocation() + offset;
                MainForm.cameraView.DownCameraReset();
            }

            //------------------- PART SPECIFIC LOGIC GOES HERE --------------------//
            if (tapeObj.PartType == "QFN")
            {
                MainForm.DisplayText("USING ENHANCE PART PICKUP", Color.HotPink);
                if (!MainForm.Cnc.CNC_XY(targetLocation))
                {
                    return(null);
                }
                // setup view
                SetCurrentTapeMeasurement(tapeObj.TapeType);
                MainForm.cameraView.downSettings.FindRectangles = true;

                // MainForm.cameraView.downVideoProcessing.FindRectangles = true;
                // move closer and get exact coordinates plus rotation
                var rect = (Shapes.Rectangle)MainForm.GoToClosestThing(Shapes.ShapeTypes.Rectangle, 1.5, .025);

                if (rect == null)
                {
                    MainForm.cameraView.DownCameraReset();
                    return(null);
                }
                Global.DoBackgroundWork(500);
                var rectAngle = rect.AngleOffsetFrom90();

                targetLocation   = rect.ToPartLocation();
                targetLocation.A = tapeObj.OriginalPartOrientationVector.ToDegrees() + rectAngle;

                MainForm.cameraView.DownCameraReset();
            }

            return(targetLocation);
        }
Пример #47
0
        public bool Move_m(double X, double Y, double A)
        {
            double dX;
            double dY;
            if (!CorrectedPosition_m(A, out dX, out dY)) return false;

            var loc = new PartLocation(X, Y, A);
            var wobble = new PartLocation(dX, dY, 0);

            var dest = loc - wobble + NeedleOffset;

            MainForm.DisplayText("== NEEDLE ==" + String.Format("pos {0} + offset {1} - wobble {2} = {3}", loc, NeedleOffset, wobble, dest), Color.ForestGreen);

            return Global.Instance.cnc.CNC_XYA(dest);
        }
        /// <summary>
        /// Map a source point to a destination point based on the calibrated inputs
        /// </summary>
        public PartLocation Map(PartLocation from)
        {
            if (Rotation == null || Offset == null) throw new Exception("LeastSquareMapping not intialized");

            var x = from.ToMatrix();
            var y = (Rotation * (x - SourceCentroid)) + Offset + SourceCentroid; //shift point to center, apply rotation, then shift to the destination

            var p = new PartLocation(y) {A = from.A + Angle};
            return p;
        }
Пример #49
0
 public Arrow(PartLocation pl, double length)
     : base(pl, PointMode.Screen)
 {
     Length = length;
 }
        public void Recomputer3()
        {
            // calculate centroids
            double sourceCentroidX = 0, sourceCentroidY = 0, destCentroidX = 0, destCentroidY = 0;

            int fiducialCount = 0;

            List <PartLocation> sourceFiducials = new List <PartLocation>();
            List <PartLocation> destFiducials   = new List <PartLocation>();

            PartLocation tempDest;

            foreach (var fiducial in source.Where(part => part.physicalComponent.IsFiducial).ToArray())
            {
                sourceCentroidX += fiducial.physicalComponent.X_nominal;
                sourceCentroidY += fiducial.physicalComponent.Y_nominal;
                sourceFiducials.Add(fiducial);

                tempDest = dest[source.IndexOf(fiducial)];

                if (tempDest.physicalComponent != null)
                {
                    destCentroidX += tempDest.physicalComponent.X_machine;
                    destCentroidY += tempDest.physicalComponent.Y_machine;
                }
                else
                {
                    destCentroidX += tempDest.X;
                    destCentroidY += tempDest.Y;
                }
                destFiducials.Add(tempDest);

                fiducialCount++;
            }
            sourceCentroidX /= fiducialCount;
            sourceCentroidY /= fiducialCount;

            destCentroidX /= fiducialCount;
            destCentroidY /= fiducialCount;

            OffsetX = -sourceCentroidX + destCentroidX;
            OffsetY = -sourceCentroidY + destCentroidY;

            List <double> destRotation   = new List <double>();
            List <double> sourceRotation = new List <double>();
            List <double> destOffset     = new List <double>();
            List <double> sourceOffset   = new List <double>();
            List <double> scale          = new List <double>();
            List <double> rotationOffset = new List <double>();

            ScaleX = 0; ScaleY = 0; Rotation_ = 0;

            // Calculate offsets from centroids, rotation from source to destination and scale difference
            PartLocation sourceFiducial = null, destFiducial = null;

            for (int i = 0; i < fiducialCount; i++)
            {
                sourceFiducial = sourceFiducials.ElementAt(i);
                destFiducial   = destFiducials.ElementAt(i);

                sourceOffset.Add(Math.Sqrt(Math.Pow(sourceFiducial.X -
                                                    sourceCentroidX, 2) + Math.Pow(sourceFiducial.Y -
                                                                                   sourceCentroidY, 2)));
                destOffset.Add(Math.Sqrt(Math.Pow(destFiducial.X -
                                                  destCentroidX, 2) + Math.Pow(destFiducial.Y -
                                                                               destCentroidY, 2)));

                sourceRotation.Add(Math.Asin((sourceFiducial.Y - sourceCentroidY) /
                                             sourceOffset[i]));
                if ((sourceFiducial.X - sourceCentroidX) < 0)
                {
                    sourceRotation[i] = Math.PI - sourceRotation[i];
                }
                if (sourceRotation[i] < 0)
                {
                    sourceRotation[i] += Math.PI * 2;
                }

                destRotation.Add(Math.Asin((destFiducial.Y - destCentroidY) /
                                           destOffset[i]));
                if ((destFiducial.X - destCentroidX) < 0)
                {
                    destRotation[i] = Math.PI - destRotation[i];
                }
                if (destRotation[i] < 0)
                {
                    destRotation[i] += Math.PI * 2;
                }

                rotationOffset.Add(destRotation[i] - sourceRotation[i]);

                scale.Add(destOffset[i] / sourceOffset[i]);

                Rotation_ += rotationOffset[i];
                ScaleX    += (destFiducial.X - destCentroidX) / (sourceFiducial.X - sourceCentroidX);
                ScaleY    += (destFiducial.Y - destCentroidY) / (sourceFiducial.Y - sourceCentroidY);
            }

            Rotation_ /= fiducialCount;
            ScaleX    /= fiducialCount;
            ScaleY    /= fiducialCount;
        }
Пример #51
0
 private void UpClickDelegate(double x, double y, int rawx, int rawy) {
     var offset = new PartLocation(x, y);
     Cnc.CNC_XY(Cnc.XYLocation + (cameraView.upVideoProcessing.mmPerPixel * offset));
 }
Пример #52
0
 public bool CNC_XYA(PartLocation loc)
 {
     if (loc==null) return false; return CNC_XYZA(loc.X, loc.Y, loc.A);
 }
Пример #53
0
        private void calibrateSkew_m()
        {
            PartLocation loc = null;
        retrySkew:
            SquareCorrection_textBox.Text = "0";
            setting.CNC_SquareCorrection = 0;
            CNC.SquareCorrection = 0;

            instructions_label.Text = "Finding center dot";

            Cnc.CNC_XY(calibrateAllStartingPoint);
            if (Cnc.Simulation)
            {
                loc = Cnc.XYLocation;
            }
            else
            {
                cameraView.SetDownCameraFunctionSet("homing");
                cameraView.downSettings.FindCircles = true;
            retryMidpoint:
                loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 2, .1);
                if (loc == null)
                {
                    ShowSimpleMessageBox("Error, middle point not found - try again");
                    return;
                }
                if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                    MessageBoxButtons.YesNo) == DialogResult.No) { goto retryMidpoint; }
            }
            calibrateAllStartingPoint = loc;

            instructions_label.Text = "Finding point at X axis";
            Cnc.CNC_XY(calibrateAllStartingPoint.X + 185.5, calibrateAllStartingPoint.Y);

            if (Cnc.Simulation)
            {
                loc = new PartLocation();
                loc.X = calibrateAllStartingPoint.X + 185.5;
                loc.Y = calibrateAllStartingPoint.Y - 1;
            }
            else
            {
            retryXPoint:
                loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 2, .1);
                if (loc == null)
                {
                    ShowSimpleMessageBox("Error, x axis point not found - try again");
                    return;
                }
                if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                    MessageBoxButtons.YesNo) == DialogResult.No) { goto retryXPoint; }
            }
            calibrateAllEdgeX = loc;

            double paperRotation;
            paperRotation = Math.Asin((calibrateAllEdgeX.X - calibrateAllStartingPoint.X) /
                Math.Sqrt(Math.Pow(calibrateAllEdgeX.X - calibrateAllStartingPoint.X, 2) +
                Math.Pow(calibrateAllEdgeX.Y - calibrateAllStartingPoint.Y, 2)));

            instructions_label.Text = "Finding point at Y axis using a calculated rotation of " +
                (paperRotation / Math.PI * 180).ToString() + " degrees";

            PartLocation projectedEdgeY = new PartLocation();

            projectedEdgeY.X = calibrateAllStartingPoint.X + 185.5 * Math.Sin(paperRotation - (Math.PI / 2));
            projectedEdgeY.Y = calibrateAllStartingPoint.Y + 185.5 * Math.Cos(paperRotation - (Math.PI / 2));

            Cnc.CNC_XY(projectedEdgeY);
            if (Cnc.Simulation)
            {
                loc = new PartLocation();
                loc.X = calibrateAllStartingPoint.X - 2;
                loc.Y = calibrateAllStartingPoint.Y + 185.5;
            }
            else
            {
                cameraView.SetDownCameraFunctionSet("homing");
                cameraView.downSettings.FindCircles = true;
            retryYPoint:
                loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 4, .1);
                if (loc == null)
                {
                    ShowSimpleMessageBox("Error, y axis point not found - try again");
                    return;
                }
                if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                    MessageBoxButtons.YesNo) == DialogResult.No) { goto retryYPoint; }
            }
            calibrateAllEdgeY = loc;

            double yOffset = calibrateAllEdgeY.Y - projectedEdgeY.Y;
            if (yOffset > 0.3 || yOffset < -0.3)
            {
                switch (ShowMessageBox("Y offset off by " + Math.Round(yOffset, 3).ToString() +
                    "mm, try again?", "Operation failed", MessageBoxButtons.AbortRetryIgnore))
                {
                    case DialogResult.Retry:
                        goto retrySkew;
                        break;
                    case DialogResult.Ignore:
                        goto ignoreSkewError;
                }
                //sender.BackColor = ChangeNeedle_button.BackColor;
                instructions_label.Text = "";
                instructions_label.Visible = false;
                calibrateAllStage = 0;
                return;
            };
        ignoreSkewError:
            double skew = (calibrateAllEdgeY.X - projectedEdgeY.X) / 185.5;
            instructions_label.Text = "Calculated skew is " + Math.Round(skew, 5).ToString()
                + ", Y offset is " + Math.Round(yOffset, 3) +
                " press next to calibrate down camera mm/pixel values";
            SquareCorrection_textBox.Text = skew.ToString();
            setting.CNC_SquareCorrection = skew;
            CNC.SquareCorrection = skew;
            Thread.Sleep(2000);

            instructions_label.Text = "Verifying data";
            calibrateAllStartingPoint.X -= calibrateAllStartingPoint.Y * setting.CNC_SquareCorrection;
            Cnc.CNC_XY(calibrateAllStartingPoint);
            loc = FindPositionAndMoveToClosest(Shapes.ShapeTypes.Circle, 4, .1);
            
            if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                MessageBoxButtons.YesNo) == DialogResult.No) { goto retrySkew; }

            calibrateAllStartingPoint = loc;

            Cnc.CNC_XY(calibrateAllStartingPoint.X + 185.5, calibrateAllStartingPoint.Y);
            if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                MessageBoxButtons.YesNo) == DialogResult.No) { goto retrySkew; }

            Cnc.CNC_XY(calibrateAllStartingPoint.X, calibrateAllStartingPoint.Y + 185.5);
            if (cameraView.ShowMessageBox("Please verify point placement. Is point found correctly?", "verification",
                MessageBoxButtons.YesNo) == DialogResult.No) { goto retrySkew; }
        }
Пример #54
0
 private bool CNC_MoveIsSafe_m(PartLocation p)
 {
     var m = Global.Instance.Locations.GetLocation("max machine");
     if ((p.X < -3.0) || (p.X > m.X) || (p.Y < -3.0) || (p.Y > m.Y)) {
         ShowSimpleMessageBox("Attempt to move outside safe limits " + p);
         return false;
     }
     if (_Zguard && IsNeedleDown()) {
         //needle is down - instead of bitching, just move it up first
         CNC_Z(0);
     }
     return true;
 }
Пример #55
0
 public void SetPosition(PartLocation loc)
 {
     if (Grid.CurrentCell == null) return;
     Nozzle selected = (Nozzle)Grid.CurrentCell.OwningRow.DataBoundItem;
     selected.setPosition(loc.X, loc.Y, 0);
 }
Пример #56
0
 public double DistanceFrom(PartLocation p)
 {
     return(DistanceFrom(p.X, p.Y));
 }
 /// <summary>
 /// The furthest distance a fiducial moved
 /// </summary>
 /// <returns></returns>
 public double MaxFiducialMovement()
 {
     //            Global.Instance.DisplayText(String.Format("Offset = {0}  Angle = {1}", new PartLocation(Offset) - Global.Instance.Locations.GetLocation("PCB Zero") , Angle), System.Drawing.Color.Purple);
     List<double> distances = new List<double>();
     for (int i = 0; i < source.Count; i++) {
         var s = new PartLocation(source[i]);
         var d = new PartLocation(dest[i]);
         var m = Map2(source[i]);
        // Global.Instance.DisplayText(String.Format("Source {0}  Dest {1}  Mapped {2}", s, d, m), System.Drawing.Color.Purple);
         distances.Add(Map2(source[i]).DistanceTo(dest[i]));
     }
     return distances.Max();
 }
Пример #58
0
 public double DistanceTo(PartLocation p)
 {
     return(Math.Sqrt(Math.Pow(X - p.X, 2) + Math.Pow(Y - p.Y, 2)));
 }
Пример #59
0
        // Part Orientation = orientation if tape is perfectly oriented the way it is oriented
        // deltaOrientation = how far offf the tape is from it's stated orientation
        public PartLocation GetPartLocation(int componentNumber)
        {
            PartLocation part;
            if (FirstPart != null) {
                part = GetPartBasedLocation(componentNumber);
            } else {
                var offset = new PartLocation(componentNumber * PartPitch + HoleToPartSpacingX, HoleToPartSpacingY);
                // add the vector to the part rotated by the tape orientation
                part = new PartLocation(FirstHole) + offset.Rotate(TapeOrientation.ToRadians());
            }
            // add deviation from expected orientation to part orientation
            var deltaOrientation = tapeOrientation.ToRadians() - OriginalTapeOrientationVector.ToRadians();
            part.A = (OriginalPartOrientationVector.ToRadians() + deltaOrientation) * 180d / Math.PI;

            return part;
        }
Пример #60
0
 public double DistanceFrom(PartLocation p)
 {
     return DistanceFrom(p.X, p.Y);
 }