예제 #1
0
        /// <summary>
        /// Construct a solid by sweeping a face in a direction.
        /// </summary>
        /// <param name="perimeter">The perimeter of the face to sweep.</param>
        /// <param name="holes">The holes of the face to sweep.</param>
        /// <param name="direction">The direction in which to sweep.</param>
        /// <param name="distance">The distance to sweep.</param>
        /// <param name="bothSides">Should the sweep start offset by direction distance/2? </param>
        /// <returns>A solid.</returns>
        public static Solid SweepFace(Polygon perimeter, Polygon[] holes, Vector3 direction, double distance, bool bothSides = false)
        {
            // We do a difference of the polygons
            // to get the clipped shape. This will fail in interesting
            // ways if the clip creates two islands.
            if (holes != null)
            {
                var newPerimeter = perimeter.Difference(holes);
                perimeter = newPerimeter[0];
                holes     = newPerimeter.Skip(1).Take(newPerimeter.Count - 1).ToArray();
            }

            var  solid  = new Solid();
            Face fStart = null;

            if (bothSides)
            {
                var t = new Transform(direction.Negated() * (distance / 2));
                if (holes != null)
                {
                    fStart = solid.AddFace(t.OfPolygon(perimeter.Reversed()), t.OfPolygons(holes.Reversed()));
                }
                else
                {
                    fStart = solid.AddFace(t.OfPolygon(perimeter.Reversed()));
                }
            }
            else
            {
                if (holes != null)
                {
                    fStart = solid.AddFace(perimeter.Reversed(), holes.Reversed());
                }
                else
                {
                    fStart = solid.AddFace(perimeter.Reversed());
                }
            }

            var fEndOuter = solid.SweepLoop(fStart.Outer, direction, distance);

            if (holes != null)
            {
                var fEndInner = new Loop[holes.Length];
                for (var i = 0; i < holes.Length; i++)
                {
                    fEndInner[i] = solid.SweepLoop(fStart.Inner[i], direction, distance);
                }
                solid.AddFace(fEndOuter, fEndInner);
            }
            else
            {
                solid.AddFace(fEndOuter);
            }

            return(solid);
        }
예제 #2
0
        /// <summary>
        /// Construct a solid by sweeping a face in a direction.
        /// </summary>
        /// <param name="outerLoop">The perimeter of the face to sweep.</param>
        /// <param name="innerLoops">The holes of the face to sweep.</param>
        /// <param name="direction">The direction in which to sweep.</param>
        /// <param name="distance">The distance to sweep.</param>
        /// <param name="bothSides">Should the sweep start offset by direction distance/2? </param>
        /// <param name="material">The solid's material.</param>
        /// <returns>A solid.</returns>
        public static Solid SweepFace(Polygon outerLoop, Polygon[] innerLoops, Vector3 direction, double distance, Material material = null, bool bothSides = false)
        {
            var  solid  = new Solid(material);
            Face fStart = null;

            if (bothSides)
            {
                var t = new Transform(direction.Negated() * (distance / 2));
                if (innerLoops != null)
                {
                    fStart = solid.AddFace(t.OfPolygon(outerLoop.Reversed()), t.OfPolygons(innerLoops.Reversed()));
                }
                else
                {
                    fStart = solid.AddFace(t.OfPolygon(outerLoop.Reversed()));
                }
            }
            else
            {
                if (innerLoops != null)
                {
                    fStart = solid.AddFace(outerLoop.Reversed(), innerLoops.Reversed());
                }
                else
                {
                    fStart = solid.AddFace(outerLoop.Reversed());
                }
            }

            var fEndOuter = solid.SweepLoop(fStart.Outer, direction, distance);

            if (innerLoops != null)
            {
                var fEndInner = new Loop[innerLoops.Length];
                for (var i = 0; i < innerLoops.Length; i++)
                {
                    fEndInner[i] = solid.SweepLoop(fStart.Inner[i], direction, distance);
                }
                solid.AddFace(fEndOuter, fEndInner);
            }
            else
            {
                solid.AddFace(fEndOuter);
            }

            return(solid);
        }
예제 #3
0
        /// <summary>
        /// Construct a solid by sweeping a face in a direction.
        /// </summary>
        /// <param name="perimeter">The perimeter of the face to sweep.</param>
        /// <param name="holes">The holes of the face to sweep.</param>
        /// <param name="direction">The direction in which to sweep.</param>
        /// <param name="distance">The distance to sweep.</param>
        /// <param name="bothSides">Should the sweep start offset by direction distance/2? </param>
        /// <param name="rotation">An optional rotation in degrees of the perimeter around the direction vector.</param>
        /// <returns>A solid.</returns>
        public static Solid SweepFace(Polygon perimeter,
                                      IList <Polygon> holes,
                                      Vector3 direction,
                                      double distance,
                                      bool bothSides  = false,
                                      double rotation = 0.0)
        {
            // We do a difference of the polygons
            // to get the clipped shape. This will fail in interesting
            // ways if the clip creates two islands.
            // if(holes != null)
            // {
            //     var newPerimeter = perimeter.Difference(holes);
            //     perimeter = newPerimeter[0];
            //     holes = newPerimeter.Skip(1).Take(newPerimeter.Count - 1).ToArray();
            // }

            var  solid  = new Solid();
            Face fStart = null;

            if (bothSides)
            {
                var t = new Transform(direction.Negate() * (distance / 2), rotation);
                if (holes != null)
                {
                    fStart = solid.AddFace(perimeter, holes, transform: t, reverse: true);
                }
                else
                {
                    fStart = solid.AddFace(perimeter, transform: t, reverse: true);
                }
            }
            else
            {
                if (holes != null)
                {
                    fStart = solid.AddFace(perimeter, holes, reverse: true);
                }
                else
                {
                    fStart = solid.AddFace(perimeter, reverse: true);
                }
            }

            var fEndOuter = solid.SweepLoop(fStart.Outer, direction, distance);

            if (holes != null)
            {
                var fEndInner = new Loop[holes.Count];
                for (var i = 0; i < holes.Count; i++)
                {
                    fEndInner[i] = solid.SweepLoop(fStart.Inner[i], direction, distance);
                }
                solid.AddFace(fEndOuter, fEndInner);
            }
            else
            {
                solid.AddFace(fEndOuter);
            }

            return(solid);
        }