//Nesting the various profiles into a polycurve segments private List <ICurve> GetProfiles(DB.RoofBase roof) { // TODO handle case if not one of our supported roofs var profiles = new List <ICurve>(); switch (roof) { case FootPrintRoof footprint: { ModelCurveArrArray crvLoops = footprint.GetProfiles(); for (var i = 0; i < crvLoops.Size; i++) { var crvLoop = crvLoops.get_Item(i); var poly = new Polycurve(ModelUnits); foreach (DB.ModelCurve curve in crvLoop) { if (curve == null) { continue; } var segment = CurveToSpeckle(curve.GeometryCurve) as Base; //it's a safe casting segment["slopeAngle"] = GetParamValue <double>(curve, BuiltInParameter.ROOF_SLOPE); segment["isSloped"] = GetParamValue <bool>(curve, BuiltInParameter.ROOF_CURVE_IS_SLOPE_DEFINING); segment["offset"] = GetParamValue <double>(curve, BuiltInParameter.ROOF_CURVE_HEIGHT_OFFSET); poly.segments.Add(segment as ICurve); //roud profiles are returned duplicated! if (curve is ModelArc arc && RevitVersionHelper.IsCurveClosed(arc.GeometryCurve)) { break; } } profiles.Add(poly); } break; } case ExtrusionRoof extrusion: { var crvloop = extrusion.GetProfile(); var poly = new Polycurve(ModelUnits); foreach (DB.ModelCurve curve in crvloop) { if (curve == null) { continue; } poly.segments.Add(CurveToSpeckle(curve.GeometryCurve)); } profiles.Add(poly); break; } } return(profiles); }
internal IList <XYZ> GetEavePointsOnOverhang(XYZ currentPointOnRidge) { IList <XYZ> ProjectedPoints = new List <XYZ>(); //XYZ currentPointOnRidge = Curve.Evaluate(Curve.GetEndParameter(0) + distanceAlongRidge, false); foreach (XYZ currentPointOnEave in ProjectRidgePointOnEaves(currentPointOnRidge)) { ModelCurveArrArray sketchModels = CurrentRoof.GetProfiles(); double minDist = double.MaxValue; ModelCurve targetEave = null; XYZ projectedPoint = null; double currentRoofTotalHeight = GetCurrentRoofHeight(); foreach (ModelCurveArray currentCurveArr in sketchModels) { foreach (ModelCurve currentCurve in currentCurveArr) { Curve targetGeoCurve = currentCurve.GeometryCurve; Line targetGeoLine = targetGeoCurve as Line; if (targetGeoLine == null) { throw new Exception("Eave is not a straight line"); } targetGeoLine = targetGeoLine.Flatten(currentRoofTotalHeight); double currentDist = targetGeoLine.Project(currentPointOnEave).Distance; if (currentDist < minDist) { minDist = currentDist; targetEave = currentCurve; projectedPoint = targetGeoLine.Project(currentPointOnEave).XYZPoint; } } } double overHang = 0; try { overHang = CurrentRoof.get_Overhang(targetEave); } catch { } currentPointOnRidge = new XYZ(currentPointOnRidge.X, currentPointOnRidge.Y, currentRoofTotalHeight); Line l = Line.CreateBound(projectedPoint, currentPointOnRidge); ProjectedPoints.Add(currentPointOnEave.Add(l.Direction.Multiply(overHang))); } return(ProjectedPoints); }
/// <summary> /// The construct of the FootPrintRoofWrapper class. /// </summary> /// <param name="roof">The footprint roof which will be edited in a PropertyGrid.</param> public FootPrintRoofWrapper(FootPrintRoof roof) { m_roof = roof; m_roofLines = new List <FootPrintRoofLine>(); ModelCurveArrArray curveloops = m_roof.GetProfiles(); foreach (ModelCurveArray curveloop in curveloops) { foreach (ModelCurve curve in curveloop) { m_roofLines.Add(new FootPrintRoofLine(m_roof, curve)); } } FootPrintRoofLineConverter.SetStandardValues(m_roofLines); m_footPrintLine = m_roofLines[0]; m_boundingbox = m_roof.get_BoundingBox(Revit.SDK.Samples.NewRoof.CS.Command.ActiveView); }
internal XYZ GetTrussTopPoint(XYZ currentPointOnRidge) { if (RoofLineType == RoofLineType.Ridge) { return(currentPointOnRidge); } //If the is not a Ridge this MUST be a SinglePanelRidge if (RoofLineType == RoofLineType.RidgeSinglePanel) { return(currentPointOnRidge); } Line currentRidgeLine = Curve.Clone() as Line; if (currentRidgeLine == null) { throw new Exception("The ridge is not a straight line!"); } ModelCurveArrArray sketchModels = CurrentRoof.GetProfiles(); double minDist = double.MaxValue; ModelCurve targetEave = null; XYZ projectedPoint = null; double currentRoofTotalHeight = GetCurrentRoofHeight(); foreach (ModelCurveArray currentCurveArr in sketchModels) { foreach (ModelCurve currentCurve in currentCurveArr) { Curve targetGeoCurve = currentCurve.GeometryCurve; Line targetGeoLine = targetGeoCurve as Line; if (targetGeoLine == null) { throw new Exception("Eave is not a straight line"); } targetGeoLine = targetGeoLine.Flatten(currentRoofTotalHeight); double currentDist = targetGeoLine.Project(currentPointOnRidge).Distance; if (currentDist < minDist) { minDist = currentDist; targetEave = currentCurve; projectedPoint = targetGeoLine.Project(currentPointOnRidge).XYZPoint; } } } double overHang = 0; try { overHang = CurrentRoof.get_Overhang(targetEave); } catch { } XYZ ridgePointFlatten = new XYZ(currentPointOnRidge.X, currentPointOnRidge.Y, currentRoofTotalHeight); //We just need to get the side that the eave is to move the point to that direction //so we dont need to get a specific eave, lets just project the first one with infinite bounds to get the direction if (RelatedRidgeEaves == null || RelatedRidgeEaves.Count == 0) { RelatedRidgeEaves = GetRelatedEaves(); } if (RelatedRidgeEaves == null || RelatedRidgeEaves.Count == 0) { throw new Exception("Related eave or eaves to current singleRidge was not found"); } Curve eaveCurve = RelatedRidgeEaves[0].AsCurve(); if (eaveCurve as Line == null) { throw new Exception("Related eave is not a straight line!"); } Line eaveLine = eaveCurve as Line; XYZ lineIntersectionPoint = GeometrySupport.GetRoofIntersectionFlattenLines(currentRidgeLine, ridgePointFlatten, eaveLine, currentRoofTotalHeight); if (lineIntersectionPoint == null) { throw new Exception("No Intersection between eave could be estabilished!"); } XYZ overHangdirection = Line.CreateBound(projectedPoint, lineIntersectionPoint).Direction.Normalize(); XYZ pointOnOverhang = projectedPoint.Add(overHangdirection.Multiply(overHang)); //We will get the point on the overhang because if we are working with a single panel ridge it may have overhangs XYZ pointOnSupport = GetSupportPoint(pointOnOverhang, currentRidgeLine.Direction.Normalize()); //Now we will shoot the point up on the Roof XYZ startingPoint = new XYZ(pointOnSupport.X, pointOnSupport.Y, pointOnSupport.Z - 1); ReferenceIntersector currentRefIntersect = new ReferenceIntersector(CurrentRoof.Id, FindReferenceTarget.Element, CurrentRoof.Document.ActiveView as View3D); ReferenceWithContext currenRefContext = currentRefIntersect.FindNearest(startingPoint, XYZ.BasisZ); if (currenRefContext == null) { return(null); } XYZ projectedPointOnRoof = currenRefContext.GetReference().GlobalPoint; return(projectedPointOnRoof); }