Example #1
0
        internal bool Add(QTPoint pt, N range, D data)
        {
            // this.HalfRange = (dynamic) range * 0.5;

            if (Point == null && Children == null) //TODO: is Children == null check neccisary?
            {
                // first time setting
                Point = pt;
                Range = range;
                Data  = data;
                ++QuadTree <N, D> .QTNodeCount;
                return(true);
            }
            else if (Point.Equals(pt)) // TODO: anything about range?
            {                          // TODO: what about if this isnt a leaf and the point matches?
                Data = data;
                return(false);
            }
            else // a leaf node or a parent node
            {
                int quad = GetQuadrant(pt);
                if (Children == null)
                {
                    Children = new QTNode <N, D> [4];
                }
                if (Children[quad] == null)
                {
                    Children[quad] = new QTNode <N, D>();
                }
                return(Children[quad].Add(pt, range, data));
            }
        }
Example #2
0
 /// <summary> <returns>
 /// True if the given point is inside the current node bounds, otherwise false.
 /// </returns> </summary>
 /// <param name="pt"></param>
 internal bool Contains(QTPoint pt)
 {
     return((dynamic)pt.X >= Point.X &&
            (dynamic)pt.X <= (dynamic)Point.X + Range &&
            (dynamic)pt.Y >= Point.Y &&
            (dynamic)pt.Y <= (dynamic)Point.Y + Range);
 }
Example #3
0
        /// <summary>
        /// Returns a point and range that captures all areas contained by both points and ranges
        /// </summary>
        /// <typeparam name="N"></typeparam>
        /// <param name="point1"></param>
        /// <param name="range1"></param>
        /// <param name="point2"></param>
        /// <param name="range2"></param>
        /// <param name="ExistingPointToChange"></param>
        /// <param name="ExistingRangeToChange"></param>
        public static void Capture(QTPoint point1, dynamic range1, QTPoint point2, dynamic range2, ref QTPoint ExistingPointToChange, ref dynamic ExistingRangeToChange)
        {
            // Get the minimum X and Y's
            ExistingPointToChange.X = point1.X < point2.X ? point1.X : point2.X;
            ExistingPointToChange.Y = point1.Y < point2.Y ? point1.Y : point2.Y;
            // Get the maximum X and Y's
            dynamic x = (point1.X + range1 > point2.X + range2 ? point1.X + range1 : point2.X + range2) - ExistingPointToChange.X;
            dynamic y = (point1.Y + range1 > point2.Y + range2 ? point1.Y + range1 : point2.Y + range2) - ExistingPointToChange.Y;

            ExistingRangeToChange = x;
        }
Example #4
0
        /// <summary>
        /// Tests if the given point range bounds overlap this current node bounds.
        /// </summary>
        /// <param name="pt"></param>
        /// <param name="otherRange"></param>
        /// <returns>True if they overlap, otherwise false.</returns>
        internal bool Overlaps(QTPoint pt, N otherRange)
        {
            // is min.rightmost > max.leftmost?
            bool XOverlap = (dynamic)Point.X <= pt.X ?
                            (dynamic)Point.X + Range > pt.X :
                            (dynamic)pt.X + otherRange > Point.X;
            // is min.topmost > max.botommost?
            bool YOverlap = (dynamic)Point.Y <= pt.Y ?
                            (dynamic)Point.Y + Range > pt.Y :
                            (dynamic)pt.Y + otherRange > Point.Y;

            // if both are true, then the two squares overlap
            return(XOverlap && YOverlap);
        }
Example #5
0
        public Image Draw(QTPoint pt, N range, Color[] DataColor)
        {
            Image    img     = new Bitmap((int)Math.Ceiling((dynamic)range), (int)Math.Ceiling((dynamic)range));
            Graphics drawing = Graphics.FromImage(img);

            //paint the background
            drawing.Clear(Color.Black);
            if (RootNode != null)
            {
                RootNode.Draw(pt, range, ref drawing, ref DataColor);
            }
            drawing.DrawImage(img, 0, 0);
            drawing.Save();
            drawing.Dispose();
            return(img);
        }
Example #6
0
 internal void Draw(QTPoint pt, N range, ref Graphics drawing, ref Color[] dataColor)
 {
     if (pt != null && Data != null)
     {
         // x y is upper left...
         drawing.FillRectangle(new System.Drawing.SolidBrush(dataColor[(dynamic)Data]), (float)Point.X, (float)((dynamic)Point.Y), (float)(dynamic)Range, (float)(dynamic)Range);
     }
     if (Children != null)
     {
         for (int i = 0; i < Children.Length; ++i)
         {
             if (Children[i] != null)
             {
                 Children[i].Draw(pt, range, ref drawing, ref dataColor);
             }
         }
     }
 }
Example #7
0
        /// <summary>
        /// Adds a point data range to the data structure.
        /// </summary>
        /// <param name="data">The data to add</param>
        /// <param name="pt">The botom left corner for the point to add</param>
        /// <param name="range">The optimal size of the box</param>
        /// <returns>True if a new point was added, false if it was a replacement or failure to add.</returns>
        public bool Add(QTPoint pt, N range, D data)
        {
            if (RootNode == null)
            {
                RootNode = new QTNode <N, D>();
                return(RootNode.Add(pt, range, data));
            }
            // If the point to add is in the current bounds, then add it.
            if (RootNode.Contains(pt)) // TODO: do i need to check if it overlaps as well or something?
            {
                return(RootNode.Add(pt, range, data));
            }
            else
            {
                // The point is out of the current bounds, we need to move the root down a level.

                // Get the range and the point for the new root node
                QTPoint NewRootPt    = new QTPoint();
                dynamic NewRootRange = 0;
                QTPoint.Capture(RootNode.Point, RootNode.Range, pt, range, ref NewRootPt, ref NewRootRange);

                // Add the current root to the new node
                QTNode <N, D> NewRoot = new QTNode <N, D>();
                if (!NewRoot.Add(pt, range, data))
                {
                    throw new Exception("How did we get here? I thought we were adding to an empty node?");
                }
                bool worked = NewRoot.Append(RootNode);
                // Update out root node
                // TODO: can optimize some lines out once we pass testing
                if (worked)
                {
                    RootNode = NewRoot;
                    return(true);
                }
                else
                {
                    throw new Exception("Why did that not work?");
                }
            }
        }
Example #8
0
        internal bool Query <C>(QTPoint pt, N range, ref C found) where C : System.Collections.ICollection
        {
            dynamic obj = found;

            if (this.Overlaps(pt, range)) // is this working?
            {
                obj.Add(Data);
                if (Children != null)
                {
                    for (int i = 0; i < 4; ++i)
                    {
                        if (Children[i] != null)
                        {
                            Children[i].Query(pt, range, ref found);
                        }
                    }
                }
                return(true);
            }
            return(false);
        }
Example #9
0
 /// <summary>
 /// Gets the data values in the given point range and puts them into the found object.
 /// </summary>
 /// <param name="pt">The bottom left point to start the search from</param>
 /// <param name="range">the size of the range tosearch for</param>
 /// <param name="found">TODO: Some sort of collection to add the found data to.</param>
 /// <returns>True if any found, false otherwise.</returns>
 public bool Query <C>(QTPoint pt, N range, ref C found) where C : System.Collections.ICollection
 {
     return(RootNode != null?RootNode.Query(pt, range, ref found) : false);
 }
Example #10
0
 public bool Find(QTPoint pt)
 {
     return(RootNode != null?RootNode.Find(pt) : false);
 }
Example #11
0
 /// <summary>
 /// ╔═════════╦══════════╗
 /// ║    3    ║     2    ║
 /// ║ TopLeft ║ TopRight ║
 /// ╠═════════╬══════════╣
 /// ║    0    ║     1    ║
 /// ║ BotLeft ║ BotRight ║
 /// ╚═════════╩══════════╝
 /// </summary>
 /// <param name="pt"></param>
 /// <returns></returns>
 internal int GetQuadrant(QTPoint pt)
 {
     // TODO: is / 2.0 or * 0.5 faster? Inital testing says they are about the same.
     return((pt.X - Point.X > (dynamic)Range * 0.5 ? 1 : 0)     // left or right
            + (pt.Y - Point.Y > (dynamic)Range * 0.5 ? 2 : 0)); // top or bottom
 }
Example #12
0
 internal bool Find(QTPoint pt)
 {
     throw new NotImplementedException();
 }