Example #1
0
 public void Store(CompressedPhoton a)
 {
     bBoxMax = new PhotonVector3(a.Position.X < bBoxMax.X ? bBoxMax.X : a.Position.X, a.Position.Y < bBoxMax.Y ? bBoxMax.Y : a.Position.Y, a.Position.Z < bBoxMax.Z ? bBoxMax.Z : a.Position.Z);
     bBoxMin = new PhotonVector3(a.Position.X > bBoxMin.X ? bBoxMin.X : a.Position.X, a.Position.Y > bBoxMin.Y ? bBoxMin.Y : a.Position.Y, a.Position.Z > bBoxMin.Z ? bBoxMin.Z : a.Position.Z);
     //store.Add(a);
     AddPhoton(a);
 }
Example #2
0
        public CompressedPhoton FindPhotonAt(PhotonVector3 location, out int comparisons)
        {
            comparisons = 0;
            Node <CompressedPhoton> cur = root;

            while (cur != null)
            {
                if (cur.Current.position[cur.Axis] == location[cur.Axis])
                {
                    if (cur.Current.position == location)
                    {
                        return(cur.Current);
                    }
                    else
                    {
                        cur = cur.Right;
                    }
                }
                else if (location[cur.Axis] < cur.Current.position[cur.Axis])
                {
                    cur = cur.Left;
                }
                else
                {
                    cur = cur.Right;
                }
                comparisons++;
            }
            return(null);
        }
Example #3
0
        public RetrievedPhotons RetrieveNearestNeighbors(PhotonVector3 point, float distanceSquared, int maxPhotons, Vector3 normal)
        {
            RetrievedPhotons _retrieved = new RetrievedPhotons(maxPhotons);

            LocatePhotons(root, point, distanceSquared, ref _retrieved, normal);

            return(_retrieved);
        }
Example #4
0
        public void Store(Photon photon)
        {
            CompressedPhoton a = new CompressedPhoton();

            if (photon.position != PhotonVector3.Empty)
            {
                a.position[0] = photon.position[0];
                a.position[1] = photon.position[1];
                a.position[2] = photon.position[2];

                for (int x = 0; x < 3; x++)
                {
                    a.Power[x] = photon.Power[x];
                }

                int theta = (int)(Math.Acos(photon.Direction[2]) * (256 / Math.PI));
                if (theta > 255)
                {
                    a.Theta = 255;
                }
                else
                {
                    a.Theta = (byte)theta;
                }

                int phi = (int)(Math.Atan2(photon.Direction[1], photon.Direction[0]) * (256 / Math.PI));
                if (phi > 255)
                {
                    a.Phi = 255;
                }
                else
                {
                    a.Phi = (byte)phi;
                }

                a.Direction = (Vector3)photon.Direction;

                for (int x = 0; x < 3; x++)
                {
                    a.Power[x] = photon.Power[x];
                }

                bBoxMax = new PhotonVector3(a.Position.X < bBoxMax.X ? bBoxMax.X : a.Position.X, a.Position.Y < bBoxMax.Y ? bBoxMax.Y : a.Position.Y, a.Position.Z < bBoxMax.Z ? bBoxMax.Z : a.Position.Z);
                bBoxMin = new PhotonVector3(a.Position.X > bBoxMin.X ? bBoxMin.X : a.Position.X, a.Position.Y > bBoxMin.Y ? bBoxMin.Y : a.Position.Y, a.Position.Z > bBoxMin.Z ? bBoxMin.Z : a.Position.Z);
                //a.LightmapIndex = photon.LightmapIndex;
                //a.MaterialIndex = photon.MaterialIndex;
                if (a == null)
                {
                    System.Diagnostics.Debugger.Break();
                }
                //this.store.Add(a);
                AddPhoton(a);
            }
            else
            {
                System.Diagnostics.Debugger.Break();
            }
        }
Example #5
0
        //List<CompressedPhoton> _retrieved;
        //PhotonVector3 _p; float _distSquared;
        public List <CompressedPhoton> RetrieveNearestNeighbors(PhotonVector3 point, float distanceSquared, int maxPhotons)
        {
            List <CompressedPhoton> _retrieved = new List <CompressedPhoton>();

            LocatePhotons(root, point, distanceSquared, ref _retrieved);
            for (int x = 0; x < _retrieved.Count; x++)
            {
            }

            return(_retrieved);
        }
Example #6
0
        //int rejected = 0;
        public void LocatePhotons(Node <CompressedPhoton> node, PhotonVector3 _p, float _distSquared, ref List <CompressedPhoton> _retrieved)
        {
            if (node == null)
            {
                return;
            }
            // Step 1: Check distance between current node and point. If it's within radius, add it.
            PhotonVector3 difference = node.Current.position - _p;
            float         dist2      = difference[0] * difference[0];

            dist2 += difference[1] * difference[1];
            dist2 += difference[2] * difference[2];

            if (dist2 < _distSquared)
            {
                if (node.Current != null)
                {
                    _retrieved.Add(node.Current);
                }
            }

            // Step 2: Is the point greater or lesser than the current node? Go left or right depending.
            if (difference[node.Axis] >= 0)
            {
                LocatePhotons(node.Right, _p, _distSquared, ref _retrieved);
                if (difference[node.Axis] * difference[node.Axis] < _distSquared)
                {
                    LocatePhotons(node.Left, _p, _distSquared, ref _retrieved);
                }
            }
            else
            {
                LocatePhotons(node.Left, _p, _distSquared, ref _retrieved);
                if (difference[node.Axis] * difference[node.Axis] < _distSquared)
                {
                    LocatePhotons(node.Right, _p, _distSquared, ref _retrieved);
                }
            }

            // Step 3: Does the radius extend past the splitting plane? If so, check the other side.
        }
Example #7
0
        public void LocatePhotons(Node <CompressedPhoton> node, PhotonVector3 _p, float _distSquared, ref RetrievedPhotons _retrieved, Vector3 normal)
        {
            if (node == null)
            {
                return;
            }
            // Step 1: Check distance between current node and point. If it's within radius, add it.
            PhotonVector3 difference = node.Current.position - _p;
            float         dist2      = difference[0] * difference[0];

            dist2 += difference[1] * difference[1];
            dist2 += difference[2] * difference[2];

            if (dist2 < _distSquared)
            {
                if ((node.Current != null) && (Vector3.Dot(node.Current.Direction, normal) < 0))
                {
                    _retrieved.AddIfClosest(node.Current, dist2);
                }
            }

            // Step 2: Is the point greater or lesser than the current node? Go left or right depending.
            if (difference[node.Axis] >= 0)
            {
                LocatePhotons(node.Right, _p, _distSquared, ref _retrieved, normal);
                if (difference[node.Axis] * difference[node.Axis] < _distSquared)
                {
                    LocatePhotons(node.Left, _p, _distSquared, ref _retrieved, normal);
                }
            }
            else
            {
                LocatePhotons(node.Left, _p, _distSquared, ref _retrieved, normal);
                if (difference[node.Axis] * difference[node.Axis] < _distSquared)
                {
                    LocatePhotons(node.Right, _p, _distSquared, ref _retrieved, normal);
                }
            }
        }
Example #8
0
        private Node <CompressedPhoton> BalanceSegment(int start, int length, PhotonVector3 bBoxMax, PhotonVector3 bBoxMin)
        {
            #region special case
            if (length <= 0)
            {
                return(null);
            }
            #endregion

            #region select dimension
            float distanceX = bBoxMax[0] - bBoxMin[0];
            float distanceY = bBoxMax[1] - bBoxMin[1];
            float distanceZ = bBoxMax[2] - bBoxMin[2];
            int   axis      = 2;

            float distance = bBoxMax[2] - bBoxMin[2];
            if (bBoxMax[1] - bBoxMin[1] > distance)
            {
                distance = bBoxMax[1] - bBoxMin[1];
                axis     = 1;
            }
            if (bBoxMax[0] - bBoxMin[0] > distance)
            {
                axis = 0;
            }
            #endregion
            int firstAxis = axis;
begin:
            #region Special case
            if (length == 1)
            {
                Node <CompressedPhoton> phot = new Node <CompressedPhoton>(store[start]);
                phot.Axis = (short)axis;
                return(phot);
            }
            #endregion

            #region find the median

            int median = start + (length >> 1); // divide by two
            if (length > 0)
            {
                //LimitedList<CompressedPhoton> newStore = new LimitedList<CompressedPhoton>(store, start, length);
                HeapSort.NewSort(store, axis, start, length);
            }

            /*else
             * QuickSort.Sort(store, start, start + length - 1, axis);*/
            /*LimitedList<CompressedPhoton> newStore = new LimitedList<CompressedPhoton>(store, start, length);
             * HeapSort.NewSort(newStore, axis);*/
            //else
            //InsertionSort.Sort(store, 0, store.Count)

            // Anything that is above or equal to the median needs to be on the right side of the root node.
            // What we are doing here is starting at the median and looking for another axis-position of the same degree to the left of the median.
            int newMedian = median;
            for (int j = median - 1; j >= start; j--)
            {
                if (store[median].position[axis] == store[j].position[axis])
                {
                    newMedian = j;
                }
            }
            median    = newMedian;
            Progress += length;
            #endregion

            #region special case

            /*if (length == 2)
             * {
             * Node<CompressedPhoton> parent = new Node<CompressedPhoton>(store[median]);
             * parent.Axis = (short)axis;
             * parent.Left = new Node<CompressedPhoton>(store[start]);
             * // TODO: Make sure this is the best way
             * parent.Left.Axis = (short)axis;
             * return parent;
             * }*/
            #endregion

            Node <CompressedPhoton> phot1 = new Node <CompressedPhoton>(store[median]);
            phot1.Axis = (short)axis;

            if (median - start > 0)
            {
                float tmp = bBoxMax[axis];
                bBoxMax[axis] = store[median].Position[axis];
                phot1.Left    = BalanceSegment(start, median - start, bBoxMax, bBoxMin);
                bBoxMax[axis] = tmp;
            }

            if (median + 1 < start + length)
            {
                if (length + start - median - 1 > 0)
                {
                    if (median == start)
                    {
                        axis = (axis + 1) % 3;
                        if (axis != firstAxis)
                        {
                            Progress -= length;
                            goto begin;
                        }
                    }
                    float tmp1 = bBoxMin[axis];
                    bBoxMin[axis] = store[median].Position[axis];
                    phot1.Right   = BalanceSegment(median + 1, length + start - median - 1, bBoxMax, bBoxMin);
                    bBoxMin[axis] = tmp1;
                }
            }

            return(phot1);
        }
Example #9
0
        public CompressedPhoton[] SortPhotons(List <CompressedPhoton> photons, Vector3 point, int maxCount)
        {
            WrapperPhoton[] array       = new WrapperPhoton[(maxCount < photons.Count) ? maxCount : photons.Count];
            PhotonVector3   photonPoint = point.ToPhotonVector();

            int end = 0;

            for (int x = 0; x < photons.Count; x++)
            {
                float dist = (photons[x].position - photonPoint).ToVector3().LengthSq();
                if (end == maxCount)
                {
                    // insert
                    int y;
                    for (y = 0; y < end; y++)
                    {
                        if (array[y].dist2 > dist)
                        {
                            break;
                        }
                    }

                    if (y >= end)
                    {
                        continue;
                    }
                    WrapperPhoton tempA, tempB;

                    tempB       = new WrapperPhoton();
                    tempB.p     = photons[x];
                    tempB.dist2 = dist;

                    for (y++; y < end; y++)
                    {
                        tempA    = array[y];
                        array[y] = tempB;
                        tempB    = tempA;
                    }
                }
                else if (end == 0)
                {
                    array[end]       = new WrapperPhoton();
                    array[end].dist2 = dist;
                    array[end].p     = photons[x];
                    end++;
                }
                else
                {
                    int y;
                    for (y = 0; y < end; y++)
                    {
                        if (array[y].dist2 > dist)
                        {
                            break;
                        }
                    }

                    if (y >= end)
                    {
                        if (end != maxCount)
                        {
                            array[end]       = new WrapperPhoton();
                            array[end].dist2 = dist;
                            array[end].p     = photons[x];
                            end++;
                        }
                        continue;
                    }
                    WrapperPhoton tempA, tempB;

                    tempB       = new WrapperPhoton();
                    tempB.p     = photons[x];
                    tempB.dist2 = dist;

                    for (y++; y < end; y++)
                    {
                        tempA    = array[y];
                        array[y] = tempB;
                        tempB    = tempA;
                    }
                    if (end != maxCount)
                    {
                        array[end] = tempB;
                        end++;
                    }
                }
            }
            CompressedPhoton[] result = new CompressedPhoton[end];
            for (int x = 0; x < end; x++)
            {
                result[x] = array[x].p;
            }
            array = null;
            //photons.Clear();
            return(result);
        }