Beispiel #1
0
 /// Returns true if any part of the two bounding boxes overlap.
 public bool Overlaps(BBox b2)
 {
     var x = Max.X >= b2.Min.X && Min.X <= b2.Max.X;
     var y = Max.Y >= b2.Min.Y && Min.Y <= b2.Max.Y;
     var z = Max.Z >= b2.Min.Z && Min.Z <= b2.Max.Z;
     return x && y && z;
 }
Beispiel #2
0
        public Scene(Primitive aggregate, IEnumerable<Light> lights, VolumeRegion volumeRegion)
        {
            _aggregate = aggregate;
            _lights = lights;
            _volumeRegion = volumeRegion;

            _worldBound = aggregate.WorldBound;
            if (volumeRegion != null)
                _worldBound = BBox.Union(_worldBound, volumeRegion.WorldBound);
        }
Beispiel #3
0
        public BBox TransformBBox(BBox b)
        {
            var ret = BBox.FromPoint(TransformPoint(new Point(b.Min.X, b.Min.Y, b.Min.Z)));

            ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Min.Y, b.Min.Z)));
            ret = BBox.Union(ret, TransformPoint(new Point(b.Min.X, b.Max.Y, b.Min.Z)));
            ret = BBox.Union(ret, TransformPoint(new Point(b.Min.X, b.Min.Y, b.Max.Z)));
            ret = BBox.Union(ret, TransformPoint(new Point(b.Min.X, b.Max.Y, b.Max.Z)));
            ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Max.Y, b.Min.Z)));
            ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Min.Y, b.Max.Z)));
            ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Max.Y, b.Max.Z)));
            return(ret);
        }
Beispiel #4
0
        public BBox MotionBounds(BBox b, bool useInverse)
        {
            if (!_actuallyAnimated)
            {
                return(Transform.Invert(_startTransform).TransformBBox(b));
            }
            BBox      ret    = BBox.Empty;
            const int nSteps = 128;

            for (int i = 0; i < nSteps; ++i)
            {
                Transform t;
                float     time = MathUtility.Lerp(i / (float)(nSteps - 1), _startTime, _endTime);
                Interpolate(time, out t);
                if (useInverse)
                {
                    t = Transform.Invert(t);
                }
                ret = BBox.Union(ret, t.TransformBBox(b));
            }
            return(ret);
        }
 public BBox MotionBounds(BBox b, bool useInverse)
 {
     if (!_actuallyAnimated)
         return Transform.Invert(_startTransform).TransformBBox(b);
     BBox ret = BBox.Empty;
     const int nSteps = 128;
     for (int i = 0; i < nSteps; ++i)
     {
         Transform t;
         float time = MathUtility.Lerp(i / (float) (nSteps - 1), _startTime, _endTime);
         Interpolate(time, out t);
         if (useInverse)
             t = Transform.Invert(t);
         ret = BBox.Union(ret, t.TransformBBox(b));
     }
     return ret;
 }
Beispiel #6
0
        public GridAccelerator(IEnumerable<Primitive> primitives, bool refineImmediately)
        {
            // Initialize _primitives_ with primitives for grid
            _primitives = refineImmediately
                ? primitives.SelectMany(prim => prim.FullyRefine()).ToArray()
                : primitives.ToArray();

            // Compute bounds and choose grid resolution
            _bounds = BBox.Empty;
            for (var i = 0; i < _primitives.Length; ++i)
                _bounds = BBox.Union(_bounds, _primitives[i].WorldBound);
            Vector delta = _bounds.Max - _bounds.Min;

            // Find _voxelsPerUnitDist_ for grid
            int maxAxis = _bounds.MaximumExtent();
            float invMaxWidth = 1.0f / delta[maxAxis];
            Debug.Assert(invMaxWidth > 0.0f);
            float cubeRoot = 3.0f * MathUtility.Pow(_primitives.Length, 1.0f / 3.0f);
            float voxelsPerUnitDist = cubeRoot * invMaxWidth;
            _numVoxels = new int[3];
            for (int axis = 0; axis < 3; ++axis)
            {
                _numVoxels[axis] = MathUtility.Round(delta[axis] * voxelsPerUnitDist);
                _numVoxels[axis] = MathUtility.Clamp(_numVoxels[axis], 1, 64);
            }

            // Compute voxel widths and allocate voxels
            for (int axis = 0; axis < 3; ++axis)
            {
                _width[axis] = delta[axis] / _numVoxels[axis];
                _inverseWidth[axis] = (_width[axis] == 0.0f) ? 0.0f : 1.0f / _width[axis];
            }
            int nv = _numVoxels[0] * _numVoxels[1] * _numVoxels[2];
            _voxels = new GridVoxel[nv];

            // Add primitives to grid voxels
            for (var i = 0; i < _primitives.Length; ++i)
            {
                // Find voxel extent of primitive
                BBox pb = _primitives[i].WorldBound;
                int[] vmin = new int[3], vmax = new int[3];
                for (int axis = 0; axis < 3; ++axis)
                {
                    vmin[axis] = PosToVoxel(ref pb.Min, axis);
                    vmax[axis] = PosToVoxel(ref pb.Max, axis);
                }

                // Add primitive to overlapping voxels
                for (int z = vmin[2]; z <= vmax[2]; ++z)
                    for (int y = vmin[1]; y <= vmax[1]; ++y)
                        for (int x = vmin[0]; x <= vmax[0]; ++x)
                        {
                            int o = Offset(x, y, z);
                            if (_voxels[o] == null)
                            {
                                // Allocate new voxel and store primitive in it
                                _voxels[o] = new GridVoxel(_primitives[i]);
                            }
                            else
                            {
                                // Add primitive to already-allocated voxel
                                _voxels[o].AddPrimitive(_primitives[i]);
                            }
                        }
            }
        }
Beispiel #7
0
 /// Creates a new bounding box padded by the given amount.
 public static BBox Expand(BBox b, float delta)
 {
     return new BBox(
         b.Min - new Vector(delta, delta, delta),
         b.Max + new Vector(delta, delta, delta));
 }
Beispiel #8
0
 /// Creates a new bounding box large enough to contain the given two
 /// bounding boxes.
 public static BBox Union(BBox b1, BBox b2)
 {
     var min = new Point(Math.Min(b1.Min.X, b2.Min.X), Math.Min(b1.Min.Y, b2.Min.Y), Math.Min(b1.Min.Z, b2.Min.Z));
     var max = new Point(Math.Max(b1.Max.X, b2.Max.X), Math.Max(b1.Max.Y, b2.Max.Y), Math.Max(b1.Max.Z, b2.Max.Z));
     return new BBox(min, max);
 }
Beispiel #9
0
 /// Creates a new bounding box large enough to contain both the original
 /// bounding box and the given point.
 public static BBox Union(BBox b, Point p)
 {
     var min = new Point(Math.Min(b.Min.X, p.X), Math.Min(b.Min.Y, p.Y), Math.Min(b.Min.Z, p.Z));
     var max = new Point(Math.Max(b.Max.X, p.X), Math.Max(b.Max.Y, p.Y), Math.Max(b.Max.Z, p.Z));
     return new BBox(min, max);
 }
Beispiel #10
0
 public AggregateVolume(IEnumerable<VolumeRegion> regions)
 {
     _regions = regions.ToList();
     _worldBound = BBox.Union(_regions.Select(x => x.WorldBound));
 }
Beispiel #11
0
 public BBox TransformBBox(BBox b)
 {
     var ret = BBox.FromPoint(TransformPoint(new Point(b.Min.X, b.Min.Y, b.Min.Z)));
     ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Min.Y, b.Min.Z)));
     ret = BBox.Union(ret, TransformPoint(new Point(b.Min.X, b.Max.Y, b.Min.Z)));
     ret = BBox.Union(ret, TransformPoint(new Point(b.Min.X, b.Min.Y, b.Max.Z)));
     ret = BBox.Union(ret, TransformPoint(new Point(b.Min.X, b.Max.Y, b.Max.Z)));
     ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Max.Y, b.Min.Z)));
     ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Min.Y, b.Max.Z)));
     ret = BBox.Union(ret, TransformPoint(new Point(b.Max.X, b.Max.Y, b.Max.Z)));
     return ret;
 }
Beispiel #12
0
 /// Creates a new bounding box padded by the given amount.
 public static BBox Expand(BBox b, float delta)
 {
     return(new BBox(
                b.Min - new Vector(delta, delta, delta),
                b.Max + new Vector(delta, delta, delta)));
 }