コード例 #1
0
 /// <summary>
 /// Constructs a new circle provider with
 /// default properties
 /// </summary>
 public CircleProvider()
 {
     Color        = FColor.Black;
     Center       = new IppiPoint_32f(0, 0);
     Radius       = 1;
     SegmentCount = 72;
 }
コード例 #2
0
 /// <summary>
 /// Constructs a new circle provider
 /// </summary>
 /// <param name="color">The (fill) color of the circle</param>
 /// <param name="center">The circles center in device coordinates</param>
 /// <param name="radius">The circles radius in device units</param>
 /// <param name="segmentCount">The number of segments to draw - more=smoother circle</param>
 public CircleProvider(FColor color, IppiPoint_32f center, float radius, ushort segmentCount)
 {
     Color        = color;
     Center       = center;
     Radius       = radius;
     SegmentCount = segmentCount;
 }
コード例 #3
0
 public PointAnalysis(IppiPoint coordinate, IppiPoint_32f smoothenedCoordinate, float instantSpeed)
 {
     CompletedBout        = null;
     OriginalCoordinate   = coordinate;
     SmoothenedCoordinate = smoothenedCoordinate;
     InstantSpeed         = instantSpeed;
 }
コード例 #4
0
 public void Precompute()
 {
     if (!Complete)
     {
         throw new InvalidOperationException("Can't precompute lookup table before completing calibration");
     }
     if (Precomputed)
     {
         return;
     }
     //create new tables
     _preCompX = new float[_scanRoi.Width * _scanRoi.Height];
     _preCompY = new float[_scanRoi.Width * _scanRoi.Height];
     //iterate over each coordinate within the image borders
     //and precompute it's voltages, storing it in the table
     for (int x = 0; x < _scanRoi.Width; x++)
     {
         for (int y = 0; y < _scanRoi.Height; y++)
         {
             IppiPoint_32f voltages = this[new IppiPoint(x + _scanRoi.X, y + _scanRoi.Y)];
             _preCompX[y * _scanRoi.Width + x] = voltages.x;
             _preCompY[y * _scanRoi.Width + x] = voltages.y;
         }
     }
     Precomputed = true;
 }
コード例 #5
0
 /// <summary>
 /// Constructs a new linear gradient provider
 /// </summary>
 /// <param name="topleft">The topleft corner of the gradient rectangle</param>
 /// <param name="width">The width of the gradient rectangle</param>
 /// <param name="height">The height of the gradient rectangle</param>
 /// <param name="colStart">The starting color of the gradient</param>
 /// <param name="colEnd">The ending color of the gradient</param>
 public LinGradientProvider(IppiPoint_32f topleft, float width, float height, FColor colStart, FColor colEnd)
 {
     Topleft  = topleft;
     Width    = width;
     Height   = height;
     ColStart = colStart;
     ColEnd   = colEnd;
 }
コード例 #6
0
 /// <summary>
 /// Constructs a new quad with the specified corners and color
 /// corners should be indicated in clock-wise direction
 /// </summary>
 /// <param name="corner1"></param>
 /// <param name="corner2"></param>
 /// <param name="corner3"></param>
 /// <param name="corner4"></param>
 /// <param name="color"></param>
 public Quad(IppiPoint_32f corner1, IppiPoint_32f corner2, IppiPoint_32f corner3, IppiPoint_32f corner4, FColor color)
 {
     Corner1 = corner1;
     Corner2 = corner2;
     Corner3 = corner3;
     Corner4 = corner4;
     Color   = color;
 }
コード例 #7
0
 /// <summary>
 /// Default constructor
 /// </summary>
 public Quad()
 {
     Corner1 = new IppiPoint_32f();
     Corner2 = new IppiPoint_32f();
     Corner3 = new IppiPoint_32f();
     Corner4 = new IppiPoint_32f();
     Color   = FColor.Black;
 }
コード例 #8
0
 /// <summary>
 /// Default constructor
 /// </summary>
 public LinGradientProvider()
 {
     Topleft  = new IppiPoint_32f(-8, -8);
     Width    = 16;
     Height   = 12;
     ColStart = FColor.Black;
     ColEnd   = FColor.White;
 }
コード例 #9
0
 /// <summary>
 /// Creates a new Luminance neutral circle provider
 /// </summary>
 /// <param name="foreground">The color of the foreground checkers</param>
 /// <param name="checkerWidth">The width of the checkers</param>
 /// <param name="checkerHeight">The height of the checkers</param>
 /// <param name="center">The center of the circle</param>
 /// <param name="radius">The radius of the circle</param>
 public LumNeutralCircleProvider(FColor foreground, float checkerWidth, float checkerHeight, IppiPoint_32f center, float radius)
 {
     Foreground    = foreground;
     CheckerWidth  = checkerWidth;
     CheckerHeight = checkerHeight;
     Center        = center;
     Radius        = radius;
     SegmentCount  = 72;
 }
コード例 #10
0
 /// <summary>
 /// Creates a new Luminance neutral circle provider
 /// </summary>
 public LumNeutralCircleProvider()
 {
     Foreground    = FColor.Red;
     CheckerWidth  = 0.1f;
     CheckerHeight = 0.1f;
     Center        = new IppiPoint_32f(0, 0);
     Radius        = 1;
     SegmentCount  = 72;
 }
コード例 #11
0
ファイル: YMazeProvider.cs プロジェクト: haesemeyer/mhapi
 /// <summary>
 /// Creates a new Y-Maze provider. The coordinates are intended to follow each other in clock-wise direction starting at the meeting point
 /// of bottom arm and left arm
 /// </summary>
 public YMazeProvider(IppiPoint_32f p1, IppiPoint_32f p2, IppiPoint_32f p3, IppiPoint_32f p4, IppiPoint_32f p5, IppiPoint_32f p6, IppiPoint_32f p7, IppiPoint_32f p8, IppiPoint_32f p9, FColor arm1, FColor arm2, FColor arm3)
 {
     _arm1     = new Quad(p1, p2, p3, p4, arm1);
     _arm2     = new Quad(p4, p5, p6, p7, arm2);
     _arm3     = new Quad(p7, p8, p9, p1, arm3);
     _vertex13 = new FColor((arm1.R + arm3.R) / 2, (arm1.G + arm3.G) / 2, (arm1.B + arm3.B) / 2);
     _vertex21 = new FColor((arm1.R + arm2.R) / 2, (arm1.G + arm2.G) / 2, (arm1.B + arm2.B) / 2);
     _vertex32 = new FColor((arm2.R + arm3.R) / 2, (arm2.G + arm3.G) / 2, (arm2.B + arm3.B) / 2);
 }
コード例 #12
0
 /// <summary>
 /// Populates a drawing provider from a string representation
 /// </summary>
 /// <param name="s">The string representation</param>
 public override void FromFileString(string s)
 {
     string[] parts = s.Split(';');
     if (parts.Length != 8 || parts[0] != "Circle")
     {
         throw new ApplicationException("Provided string does not represent a CircleProvider");
     }
     Color        = new FColor(float.Parse(parts[1]), float.Parse(parts[2]), float.Parse(parts[3]));
     Radius       = float.Parse(parts[4]);
     Center       = new IppiPoint_32f(float.Parse(parts[5]), float.Parse(parts[6]));
     SegmentCount = ushort.Parse(parts[7]);
 }
コード例 #13
0
 public override void FromFileString(string s)
 {
     string[] parts = s.Split(';');
     if (parts.Length != 11 || parts[0] != "LinGrad")
     {
         throw new ApplicationException("Provided string does not represent a FourSquareProvider");
     }
     Topleft  = new IppiPoint_32f(float.Parse(parts[1]), float.Parse(parts[2]));
     Width    = float.Parse(parts[3]);
     Height   = float.Parse(parts[4]);
     ColStart = new FColor(float.Parse(parts[5]), float.Parse(parts[6]), float.Parse(parts[7]));
     ColEnd   = new FColor(float.Parse(parts[8]), float.Parse(parts[9]), float.Parse(parts[10]));
 }
コード例 #14
0
 public override IppiPoint_32f this[IppiPoint p]
 {
     get
     {
         if (p.x >= _imageWidth || p.x < 0 || p.y >= _imageHeight || p.y < 0)
         {
             throw new ArgumentOutOfRangeException("Requested coordinate is outside of the calibrated image dimensions");
         }
         if (!Complete)
         {
             throw new NotSupportedException("Can't obtain voltages before calibration");
         }
         IppiPoint_32f retval = new IppiPoint_32f(_xVolts[p.x], _yVolts[p.y]);
         return(retval);
     }
 }
コード例 #15
0
 /// <summary>
 /// Method to perform all necessary steps to find one calibration point
 /// in three-point calibration
 /// </summary>
 /// <param name="frame">Frame number 0-based from start of operation</param>
 /// <param name="camImage">The current camera image</param>
 /// <param name="voltages">The voltages to move laser to</param>
 /// <returns>-1,-1 or the identified point</returns>
 protected IppiPoint MoveAndDetect(int frame, Image8 camImage, IppiPoint_32f voltages)
 {
     if (frame < Properties.Settings.Default.FrameRate / 10)
     {
         //In the first 100 ms we just give the scanner ample time to reach the target
         _scanner.Hit(voltages);
         return(new IppiPoint(-1, -1));
     }
     else if (frame < Properties.Settings.Default.FrameRate * 1.1)
     {
         //In the next second we build our foreground
         _laser.LaserPower = Properties.Settings.Default.LaserCalibPowermW;
         _fgModel.UpdateBackground(camImage);
         return(new IppiPoint(-1, -1));
     }
     else
     {
         //Let's find the beam location and return it
         return(FindBeamLocation(_fgModel.Background, _bgModel.Background, _calc, _foreground));
     }
 }
コード例 #16
0
 /// <summary>
 /// Rotates the mirrors according to given voltages
 /// </summary>
 /// <param name="voltages">The x/y voltages to apply to the servo controllers</param>
 /// <returns>The status code of the targeting attempt</returns>
 public HitStatus Hit(IppiPoint_32f voltages)
 {
     if (voltages.x < VMin || voltages.y < VMin || voltages.x > VMax || voltages.y > VMax)
     {
         return(HitStatus.OutOfRange);
     }
     try
     {
         //_xWriter.WriteSingleSample(true, voltages.x);
         //_yWriter.WriteSingleSample(true, voltages.y);
         double[] volts = new double[2];
         volts[0] = voltages.x;
         volts[1] = voltages.y;
         _multiWriter.WriteSingleSample(true, volts);
     }
     catch (Exception e)
     {
         System.Diagnostics.Debug.WriteLine(e);
         return(HitStatus.Exception);
     }
     return(HitStatus.Success);
 }
コード例 #17
0
        /// <summary>
        /// Tests the connection with the mirror setup reading position
        /// values back from the indicated analog in channels on the indicated device
        /// </summary>
        /// <param name="aiDevice">The NI board to connect to (f.e. "dev1")</param>
        /// <param name="aiX">The analog in that reads x-mirror position (f.e. "ai0")</param>
        /// <param name="aiY">The analog in that reads y-mirror position (f.e. "ai1")</param>
        /// <param name="scaleFactor">The scale factor between supplied ao-voltage and the corresponding ai-voltage supplied by the breakout board (scale = V(ai)/V(a0))</param>
        /// <returns>True if successfull</returns>
        public bool TestConnection(string aiDevice, string aiX, string aiY, double scaleFactor)
        {
            string connectX = aiDevice + '/' + aiX;
            string connectY = aiDevice + '/' + aiY;
            Task   mirrorPosTask = new Task("mirrorRead");
            var    samples = new double[2, 100]; //in each read we read 10 samples from 2 analog ins (mirrorX and mirrorY)
            double avgx, avgy;                   //the averages of the read voltages for both mirrors

            mirrorPosTask.AIChannels.CreateVoltageChannel(connectX, "ChanXMirror", AITerminalConfiguration.Differential, -10, 10, AIVoltageUnits.Volts);
            mirrorPosTask.AIChannels.CreateVoltageChannel(connectY, "ChanYMirror", AITerminalConfiguration.Differential, -10, 10, AIVoltageUnits.Volts);
            mirrorPosTask.Timing.ConfigureSampleClock("", 100, SampleClockActiveEdge.Rising, SampleQuantityMode.FiniteSamples, 100);
            AnalogMultiChannelReader aiReader = new AnalogMultiChannelReader(mirrorPosTask.Stream);
            //hit first point
            IppiPoint_32f target = new IppiPoint_32f(-5, -5);

            Hit(target);
            System.Threading.Thread.Sleep(10);//give mirrors time to settle
            mirrorPosTask.Start();
            while (mirrorPosTask.Stream.AvailableSamplesPerChannel < 100)
            {
            }                                                                //wait until all samples are acquired
            //read mirror position back
            samples = aiReader.ReadMultiSample(100);
            mirrorPosTask.Stop();
            avgx = avgy = 0;
            for (int i = 0; i < 100; i++)
            {
                avgx += (samples[0, i] / 100);
                avgy += (samples[1, i] / 100);
            }
            if (Math.Round(avgx / scaleFactor) != -5 || Math.Round(avgy / scaleFactor) != -5)
            {
                mirrorPosTask.Dispose();
                return(false);
            }
            //hit second point
            target.x = 5;
            target.y = 5;
            Hit(target);
            System.Threading.Thread.Sleep(10);//give mirrors time to settle
            mirrorPosTask.Start();
            while (mirrorPosTask.Stream.AvailableSamplesPerChannel < 100)
            {
            }                                                                //wait until all samples are acquired
            //read mirror position back
            samples = aiReader.ReadMultiSample(100);
            mirrorPosTask.Stop();
            avgx = avgy = 0;
            for (int i = 0; i < 100; i++)
            {
                avgx += (samples[0, i] / 100);
                avgy += (samples[1, i] / 100);
            }
            if (Math.Round(avgx / scaleFactor) != 5 || Math.Round(avgy / scaleFactor) != 5)
            {
                mirrorPosTask.Dispose();
                return(false);
            }
            mirrorPosTask.Dispose();
            return(true);
        }
コード例 #18
0
        /*
         * /// <summary>
         * /// The width of the border within which we calibrated
         * /// </summary>
         * public int Border
         * {
         *  get
         *  {
         *      return _border;
         *  }
         * }
         */


        /// <summary>
        /// For a given point returns the corresponding
        /// x and y voltages
        /// </summary>
        /// <param name="p">The coordinate to look up</param>
        /// <returns>A 2 element array containing the x-voltage and y-voltage</returns>
        public override IppiPoint_32f this[IppiPoint p]
        {
            get
            {
                if (!_complete)
                {
                    throw new InvalidOperationException("Tried to use non-complete calibration table");
                }
                IppiPoint_32f retval = new IppiPoint_32f();
                if (p.x < _scanRoi.X || p.x >= (_scanRoi.Width + _scanRoi.X))
                {
                    throw new ArgumentOutOfRangeException("X coordinate outside lookup table area");
                }
                if (p.y < _scanRoi.Y || p.y >= (_scanRoi.Height + _scanRoi.Y))
                {
                    throw new ArgumentOutOfRangeException("Y coordinate outside lookup table area");
                }
                if (Precomputed)
                {
                    //our precomputed lookup table has a size equal to the ROI size
                    //therefore we need to deduct the ROI start from the point
                    //coordinates
                    p.x      = p.x - _scanRoi.X;
                    p.y      = p.y - _scanRoi.Y;
                    retval.x = _preCompX[p.y * _scanRoi.Width + p.x];
                    retval.y = _preCompY[p.y * _scanRoi.Width + p.x];
                    return(retval);
                }
                int xIn, yIn;
                //correct for the border presence
                xIn = p.x - _scanRoi.X;
                yIn = p.y - _scanRoi.Y;
                //find table coordinates of the closest points with LOWER coordinates
                //then the other borders will be +1 from that
                int xTabLeft, yTabTop, xTabRight, yTabBottom;
                xTabLeft   = xIn / _spacing;
                yTabTop    = yIn / _spacing;
                xTabRight  = xTabLeft + 1;
                yTabBottom = yTabTop + 1;
                if (xTabLeft * _spacing == xIn && yTabTop * _spacing == yIn)
                {
                    //we don't need to interpolate
                    retval.x = _xVolts[yTabTop * _c + xTabLeft];
                    retval.y = _yVolts[yTabTop * _c + xTabLeft];
                    return(retval);
                }
                else if (xTabLeft * _spacing == xIn)
                {
                    //we only need to interpolate along y
                    int ydist = yIn - yTabTop * _spacing;
                    //the larger the distance, the more we weigh in the value from the bottom point
                    float bottomFrac = (float)ydist / (float)_spacing;
                    retval.x = _xVolts[yTabTop * _c + xTabLeft] * (1 - bottomFrac) + _xVolts[yTabBottom * _c + xTabLeft] * bottomFrac;
                    retval.y = _yVolts[yTabTop * _c + xTabLeft] * (1 - bottomFrac) + _yVolts[yTabBottom * _c + xTabLeft] * bottomFrac;
                    return(retval);
                }
                else if (yTabTop * _spacing == yIn)
                {
                    //we only need to interpolate along x
                    int xdist = xIn - xTabLeft * _spacing;
                    //the larger the distance the more we weigh in the value from the right point
                    float rightFrac = (float)xdist / (float)_spacing;
                    retval.x = _xVolts[yTabTop * _c + xTabLeft] * (1 - rightFrac) + _xVolts[yTabTop * _c + xTabRight] * rightFrac;
                    retval.y = _yVolts[yTabTop * _c + xTabLeft] * (1 - rightFrac) + _yVolts[yTabTop * _c + xTabRight] * rightFrac;
                    return(retval);
                }
                else
                {
                    //bilinear interpolation
                    float[] top, bottom;
                    top    = new float[2];
                    bottom = new float[2];
                    int xdist = xIn - xTabLeft * _spacing;
                    //the larger the distance the more we weigh in the value from the right point
                    float rightFrac = (float)xdist / (float)_spacing;
                    int   ydist     = yIn - yTabTop * _spacing;
                    //the larger the distance, the more we weigh in the value from the bottom point
                    float bottomFrac = (float)ydist / (float)_spacing;
                    //first we interpolate along x for both top and bottom
                    top[0]    = _xVolts[yTabTop * _c + xTabLeft] * (1 - rightFrac) + _xVolts[yTabTop * _c + xTabRight] * rightFrac;
                    top[1]    = _yVolts[yTabTop * _c + xTabLeft] * (1 - rightFrac) + _yVolts[yTabTop * _c + xTabRight] * rightFrac;
                    bottom[0] = _xVolts[yTabBottom * _c + xTabLeft] * (1 - rightFrac) + _xVolts[yTabBottom * _c + xTabRight] * rightFrac;
                    bottom[1] = _yVolts[yTabBottom * _c + xTabLeft] * (1 - rightFrac) + _yVolts[yTabBottom * _c + xTabRight] * rightFrac;
                    //now we interpolate between top and bottom
                    retval.x = top[0] * (1 - bottomFrac) + bottom[0] * bottomFrac;
                    retval.y = top[1] * (1 - bottomFrac) + bottom[1] * bottomFrac;
                    return(retval);
                }
            }
        }
コード例 #19
0
 /// <summary>
 /// Computes the Euclidian distance between two points
 /// </summary>
 /// <param name="p1">Point1</param>
 /// <param name="p2">Point2</param>
 /// <returns>The euclidian distance</returns>
 public static double Euclidian(IppiPoint_32f p1, IppiPoint_32f p2)
 {
     return(Math.Sqrt((p1.x - p2.x) * (p1.x - p2.x) + (p1.y - p2.y) * (p1.y - p2.y)));
 }