예제 #1
0
        private bool GetInnerBoundary()
        {
            //plot 의 boundary 와 roads 를 사용.
            var segments = boundary.DuplicateSegments();

            double offsetDistance = UnderGroundParkingConsts.Clearance;

            for (int i = 0; i < segments.Length; i++)
            {
                Curve temp = segments[i];
                var   v    = temp.TangentAtStart;
                v.Rotate(-Math.PI / 2, Vector3d.ZAxis);
                temp.Translate(v * offsetDistance);
                segments[i] = temp;
            }

            List <Point3d> topoly = new List <Point3d>();

            for (int k = 0; k < segments.Length; k++)
            {
                int  j  = (k + 1) % segments.Length;
                Line li = new Line(segments[k].PointAtStart, segments[k].PointAtEnd);
                Line lj = new Line(segments[j].PointAtStart, segments[j].PointAtEnd);

                double paramA;
                double paramB;
                var    intersect = Rhino.Geometry.Intersect.Intersection.LineLine(li, lj, out paramA, out paramB, 0, false);

                // 교점이 A 선 위에 있음
                bool isparamAonA = paramA >= 0 && paramA <= 1 ? true : false;
                // 교점이 B 선 위에 있음
                bool isparamBonB = paramB >= 0 && paramB <= 1 ? true : false;

                bool isRightSided = paramA > 1 && paramB > 1 ? true : false;
                bool isLeftSided  = paramA < 0 && paramB < 0 ? true : false;
                // A 나 B 둘중 한 선의 위에.
                if (isparamAonA && !isparamBonB || !isparamAonA && isparamBonB)
                {
                    topoly.Add(li.PointAt(paramA));
                    //topoly.Add(segments[k].PointAtEnd);
                    //topoly.Add(segments[j].PointAtStart);
                    //k의 endpoint 에서 j의 startpoint로 선 긋는다.
                }
                // 두 선 위의 교점에.
                else if (isparamAonA && isparamBonB)
                {
                    //교점을 더함
                    topoly.Add(li.PointAt(paramA));
                }
                //외부에
                else
                {
                    //오른쪽 치우침
                    if (isRightSided)
                    {
                        topoly.Add(segments[k].PointAtEnd);
                        topoly.Add(segments[j].PointAtStart);
                    }
                    //왼쪽 치우침
                    else if (isLeftSided)
                    {
                        topoly.Add(segments[k].PointAtEnd);
                        topoly.Add(segments[j].PointAtStart);
                    }
                    //일반
                    else
                    {
                        topoly.Add(li.PointAt(paramA));
                    }
                }
            }
            topoly.Add(topoly[0]);
            var tempcurve        = new PolylineCurve(topoly);
            var rotation         = tempcurve.ClosedCurveOrientation(Vector3d.ZAxis);
            var selfintersection = Rhino.Geometry.Intersect.Intersection.CurveSelf(tempcurve, 0);
            var parameters       = selfintersection.Select(n => n.ParameterA).ToList();

            parameters.AddRange(selfintersection.Select(n => n.ParameterB));
            var spl    = tempcurve.Split(parameters);
            var f      = CommonFunc.NewJoin(spl);
            var merged = f.Where(n => n.ClosedCurveOrientation(Vector3d.ZAxis) == rotation).ToList();

            if (merged.Count == 0)
            {
                return(false);
            }

            merged        = merged.OrderByDescending(n => n.GetArea()).ToList();
            innerBoundary = merged[0];
            return(true);
        }
예제 #2
0
파일: Regulation.cs 프로젝트: 11o9/NG
        //채광방향
        public static List <Curve> Lighting(Curve roadCenter, Plot plot, double aptAngle)
        {
            double d = 0;

            if (plot.PlotType != PlotTypes.상업지역)
            {
                if (plot.LegalMaxF <= 7)
                {
                    d = 0.25;
                }
                else
                {
                    d = 0.5;
                }
            }
            else
            {
                d = 0.25;
            }

            Curve basecurve = null;
            var   cp        = AreaMassProperties.Compute(plot.Boundary).Centroid;
            var   basev     = Vector3d.XAxis;

            basev.Rotate(aptAngle, Vector3d.ZAxis);
            var bounding = plot.Boundary.GetBoundingBox(false);

            basecurve = new LineCurve(cp - basev * bounding.Diagonal.Length / 2, cp + basev * bounding.Diagonal.Length / 2);

            List <Curve> result  = new List <Curve>();
            Curve        last    = roadCenter.DuplicateCurve();
            double       pheight = 3.3;
            double       fheight = 2.8;
            int          floor   = plot.LegalMaxF;

            List <Curve> debug = new List <Curve>();

            for (int i = 0; i < floor; i++)
            {
                var height   = pheight + fheight * i;
                var distance = d * (height - pheight);

                var segments = roadCenter.DuplicateSegments();
                for (int j = 0; j < segments.Length; j++)
                {
                    var ps = segments[j].PointAtStart;
                    var pe = segments[j].PointAtEnd;

                    double ds = 0;
                    double de = 0;


                    basecurve.ClosestPoint(ps, out ds);
                    basecurve.ClosestPoint(pe, out de);

                    Vector3d vs = basecurve.PointAt(ds) - ps;
                    Vector3d ve = basecurve.PointAt(de) - pe;
                    vs.Unitize();
                    ve.Unitize();

                    var mp = segments[j].PointAtNormalizedLength(0.5);
                    var ts = mp + vs;
                    var te = mp + ve;

                    if (roadCenter.Contains(ts) == PointContainment.Inside)
                    {
                        segments[j].Translate(vs * distance);
                    }
                    else if (roadCenter.Contains(te) == PointContainment.Inside)
                    {
                        segments[j].Translate(ve * distance);
                    }

                    segments[j].Translate(Vector3d.ZAxis * height);
                }

                List <Point3d> topoly = new List <Point3d>();
                for (int k = 0; k < segments.Length; k++)
                {
                    int    j  = (k + 1) % segments.Length;
                    Line   li = new Line(segments[k].PointAtStart, segments[k].PointAtEnd);
                    Line   lj = new Line(segments[j].PointAtStart, segments[j].PointAtEnd);
                    double paramA;
                    double paramB;
                    var    intersect = Rhino.Geometry.Intersect.Intersection.LineLine(li, lj, out paramA, out paramB, 0, false);

                    topoly.Add(li.PointAt(paramA));
                }

                topoly.Add(topoly[0]);
                var tempcurve        = new PolylineCurve(topoly);
                var rotation         = tempcurve.ClosedCurveOrientation(Vector3d.ZAxis);
                var selfintersection = Rhino.Geometry.Intersect.Intersection.CurveSelf(tempcurve, 0);

                var parameters = selfintersection.Select(n => n.ParameterA).ToList();

                parameters.AddRange(selfintersection.Select(n => n.ParameterB));

                var spl = tempcurve.Split(parameters);

                var f = NewJoin(spl);


                var merged = f.Where(n => n.ClosedCurveOrientation(Vector3d.ZAxis) == rotation).ToList();
                debug.AddRange(merged);


                for (int j = merged.Count - 1; j >= 0; j--)
                {
                    var tc = merged[j].DuplicateCurve();
                    tc.Translate(Vector3d.ZAxis * -tc.PointAtStart.Z);

                    if (Curve.CreateBooleanDifference(tc, last).Length == 0)
                    {
                        last = tc;
                        result.Add(merged[j]);
                    }
                }
            }

            return(result);
        }