private Reference GetFaceRef(Element e) { Options geomOption = Doc.Application.Create.NewGeometryOptions(); geomOption.ComputeReferences = true; geomOption.IncludeNonVisibleObjects = true; geomOption.DetailLevel = ViewDetailLevel.Fine; GeometryElement ge = e.get_Geometry(geomOption); foreach (GeometryObject geomObj in ge) { Solid geomSolid = geomObj as Solid; if (null != geomSolid) { foreach (Face geomFace in geomSolid.Faces) { if (FaceWall.IsValidFaceReferenceForFaceWall(Doc, geomFace.Reference)) { return(geomFace.Reference); } } } } return(null); }
private static List <Face3D> Profiles_FaceWall(this FaceWall faceWall) { GeometryElement geometryElement = faceWall.get_Geometry(new Options()); if (geometryElement == null) { return(null); } List <Face3D> result = new List <Face3D>(); foreach (GeometryObject geometryObject in geometryElement) { Type aType = geometryObject.GetType(); if (geometryObject is Autodesk.Revit.DB.Face) { } else if (geometryObject is Solid) { } else if (geometryObject is Curve) { } } return(null); }
public void ByFace_ShouldCreateFaceWall() { Element elem = ElementSelector.ByElementId(205302); var refr = elem.ElementFaceReferences[0].InternalReference; var wallType = WallType.ByName("Generic - 5\""); FaceWall wall = FaceWall.ByFace(Autodesk.Revit.DB.WallLocationLine.CoreCenterline, wallType, refr); Assert.NotNull(wall); Assert.AreEqual(wall.GetType(), typeof(FaceWall)); Assert.NotNull(wall.InternalElement); }
// By Harry Mattison, Boost Your BIM, // Automating the Building Maker workflow // https://boostyourbim.wordpress.com/2014/02/11/automating-the-building-maker-workflow/ // Face Wall and Mass Floor creation with the Revit API // https://youtu.be/nHWen2_lN6U /// <summary> /// Create face walls and mass floors on and in selected mass element /// </summary> public void CreateFaceWallsAndMassFloors(UIDocument uidoc) { Document doc = uidoc.Document; FamilyInstance fi = doc.GetElement( uidoc.Selection.PickObject( ObjectType.Element)) as FamilyInstance; WallType wType = new FilteredElementCollector(doc) .OfClass(typeof(WallType)) .Cast <WallType>().FirstOrDefault(q => q.Name == "Generic - 6\" Masonry"); Options opt = new Options(); opt.ComputeReferences = true; using (Transaction t = new Transaction(doc)) { t.Start("Create Face Walls & Mass Floors"); foreach (Solid solid in fi.get_Geometry(opt) .Where(q => q is Solid).Cast <Solid>()) { foreach (Face f in solid.Faces) { if (FaceWall.IsValidFaceReferenceForFaceWall( doc, f.Reference)) { FaceWall.Create(doc, wType.Id, WallLocationLine.CoreExterior, f.Reference); } } } FilteredElementCollector levels = new FilteredElementCollector(doc) .OfClass(typeof(Level)); foreach (Level level in levels) { MassInstanceUtils.AddMassLevelDataToMassInstance( doc, fi.Id, level.Id); } t.Commit(); } }
/// <summary> /// Prompting the user to pick a wall face /// </summary> /// <returns> /// Returns 'Cancelled' if the end-user escapes from face picking. /// Otherwise returns Succeeded or Failed depending on whether /// a face on a wall or face-wall was picked as expected /// </returns> private Result PickWallFace(UIDocument uidoc, out String sref) { sref = null; Reference faceref = null; try { faceref = uidoc.Selection.PickObject(ObjectType.Face, "Pick a face on a wall or face-wall element."); } catch (Autodesk.Revit.Exceptions.OperationCanceledException) { return(Result.Cancelled); } // we make sure we have the expected kind of face reference if (faceref != null) { Element pickedelem = uidoc.Document.GetElement(faceref.ElementId); FaceWall asfacewall = pickedelem as FaceWall; Wall aswall = pickedelem as Wall; // in this particular example, we accepts faces on wall elements only if ((aswall == null) && (asfacewall == null)) { return(Result.Failed); } } // we convert the reference object to a more stable string // representation that is more traceable across transactions sref = faceref.ConvertToStableRepresentation(uidoc.Document); return(Result.Succeeded); }
public static void SlopedWallTest( ExternalCommandData revit) { Document massDoc = revit.Application.Application.NewFamilyDocument( @"C:\ProgramData\Autodesk\RAC 2012\Family Templates\English_I\Conceptual Mass\Mass.rft"); Transaction transaction = new Transaction(massDoc); transaction.SetName("TEST"); transaction.Start(); ExternalCommandData cdata = revit; Autodesk.Revit.ApplicationServices.Application app = revit.Application.Application; app = revit.Application.Application; // Create one profile ReferenceArray ref_ar = new ReferenceArray(); Autodesk.Revit.DB.XYZ ptA = new XYZ(0, 0, 0); XYZ ptB = new XYZ(0, 30, 0); ModelCurve modelcurve = MakeLine(revit.Application, ptA, ptB, massDoc); ref_ar.Append(modelcurve.GeometryCurve.Reference); ptA = new XYZ(0, 30, 0); ptB = new XYZ(2, 30, 0); modelcurve = MakeLine(revit.Application, ptA, ptB, massDoc); ref_ar.Append(modelcurve.GeometryCurve.Reference); ptA = new XYZ(2, 30, 0); ptB = new XYZ(2, 0, 0); modelcurve = MakeLine(revit.Application, ptA, ptB, massDoc); ref_ar.Append(modelcurve.GeometryCurve.Reference); ptA = new XYZ(2, 0, 0); ptB = new XYZ(0, 0, 0); modelcurve = MakeLine(revit.Application, ptA, ptB, massDoc); ref_ar.Append(modelcurve.GeometryCurve.Reference); // The extrusion form direction XYZ direction = new XYZ(-6, 0, 50); Form form = massDoc.FamilyCreate.NewExtrusionForm(true, ref_ar, direction); transaction.Commit(); if (File.Exists(@"C:\TestFamily.rfa")) { File.Delete(@"C:\TestFamily.rfa"); } massDoc.SaveAs(@"C:\TestFamily.rfa"); if (!revit.Application.ActiveUIDocument.Document.LoadFamily(@"C:\TestFamily.rfa")) { throw new Exception("DID NOT LOAD FAMILY"); } Family family = null; foreach (Element el in new FilteredElementCollector( revit.Application.ActiveUIDocument.Document).WhereElementIsNotElementType().ToElements()) { if (el is Family) { if (((Family)el).Name.ToUpper().Trim().StartsWith("TEST")) { family = (Family)el; } } } FamilySymbol fs = null; foreach (FamilySymbol sym in family.Symbols) { fs = sym; } // Create a family instance. revit.Application.ActiveUIDocument.Document.Create.NewFamilyInstance( new XYZ(0, 0, 0), fs, revit.Application.ActiveUIDocument.Document.ActiveView.Level, StructuralType.NonStructural); WallType wallType = null; foreach (WallType wt in revit.Application.ActiveUIDocument.Document.WallTypes) { if (FaceWall.IsWallTypeValidForFaceWall(revit.Application.ActiveUIDocument.Document, wt.Id)) { wallType = wt; break; } } foreach (Element el in new FilteredElementCollector( revit.Application.ActiveUIDocument.Document).WhereElementIsNotElementType().ToElements()) { if (el is FamilyInstance) { if (((FamilyInstance)el).Symbol.Family.Name.ToUpper().StartsWith("TEST")) { Options options = revit.Application.Application.Create.NewGeometryOptions(); options.ComputeReferences = true; options.View = revit.Application.ActiveUIDocument.Document.ActiveView; GeometryElement geoel = el.get_Geometry(options); // Attempt to create a slopped wall from the geometry. for (int i = 0; i < geoel.Objects.Size; i++) { if (geoel.Objects.get_Item(i) is Solid) { Solid solid = (Solid)geoel.Objects.get_Item(i); for (int j = 0; j < solid.Faces.Size; j++) { try { if (solid.Faces.get_Item(i).Reference != null) { FaceWall.Create(revit.Application.ActiveUIDocument.Document, wallType.Id, WallLocationLine.CoreCenterline, solid.Faces.get_Item(i).Reference); } } catch (System.Exception e) { System.Windows.Forms.MessageBox.Show(e.Message); } } } } } } } }
static void CreateFaceWalls( Document doc) { Application app = doc.Application; Document massDoc = app.NewFamilyDocument( _conceptual_mass_template_path); CreateMassExtrusion(massDoc); //if( File.Exists( _family_path ) ) // File.Delete( _family_path ); SaveAsOptions opt = new SaveAsOptions(); opt.OverwriteExistingFile = true; massDoc.SaveAs(_family_path, opt); using (Transaction tx = new Transaction(doc)) { tx.Start("Create FaceWall"); if (!doc.LoadFamily(_family_path)) { throw new Exception("DID NOT LOAD FAMILY"); } Family family = new FilteredElementCollector(doc) .OfClass(typeof(Family)) .Where <Element>(x => x.Name.Equals(_family_name)) .Cast <Family>() .FirstOrDefault(); FamilySymbol fs = doc.GetElement( family.GetFamilySymbolIds().First <ElementId>()) as FamilySymbol; // Create a family instance Level level = doc.ActiveView.GenLevel; FamilyInstance fi = doc.Create.NewFamilyInstance( XYZ.Zero, fs, level, StructuralType.NonStructural); doc.Regenerate(); // required to generate the geometry! // Determine wall type. WallType wallType = new FilteredElementCollector(doc) .OfClass(typeof(WallType)) .Cast <WallType>() .Where <WallType>(x => FaceWall.IsWallTypeValidForFaceWall(doc, x.Id)) .FirstOrDefault(); // Retrieve mass element geometry. Options options = app.Create.NewGeometryOptions(); options.ComputeReferences = true; //options.View = doc.ActiveView; // conceptual mass is not visible in default view GeometryElement geo = fi.get_Geometry(options); // Create a sloped wall from the geometry. foreach (GeometryObject obj in geo) { Solid solid = obj as Solid; if (null != solid) { foreach (Face f in solid.Faces) { Debug.Assert(null != f.Reference, "we asked for references, didn't we?"); PlanarFace pf = f as PlanarFace; if (null != pf) { XYZ v = pf.FaceNormal; // Errors: // // Could not create a face wall. // // Caused by using ActiveView.Level // instead of ActiveView.GenLevel. // // This reference cannot be applied to a face wall. // // Caused by using this on a horizontal face. if (!Util.IsVertical(v)) { FaceWall.Create( doc, wallType.Id, WallLocationLine.CoreCenterline, f.Reference); } } } } } tx.Commit(); } }
//TODO: delete temp family after creation //TODO: allow updates to family..? //NOTE: FaceWalls cannot be updated, as well we can't seem to get their base face easily so they are ToNatvie only public List <ApplicationPlaceholderObject> FaceWallToNative(RevitFaceWall speckleWall) { if (speckleWall.surface == null) { throw new Speckle.Core.Logging.SpeckleException("Only surface based FaceWalls are currently supported."); } // Cannot update revit wall to new mass face FaceWall revitWall = GetExistingElementByApplicationId(speckleWall.applicationId) as DB.FaceWall; if (revitWall != null) { Doc.Delete(revitWall.Id); } var famPath = Path.Combine(Doc.Application.FamilyTemplatePath, @"Conceptual Mass\Metric Mass.rft"); if (!File.Exists(famPath)) { ConversionErrors.Add(new Error { message = $"Could not find file Metric Mass.rft" }); return(null); } var tempMassFamilyPath = CreateMassFamily(famPath, speckleWall.surface, speckleWall.applicationId); Family fam; Doc.LoadFamily(tempMassFamilyPath, new FamilyLoadOption(), out fam); var symbol = Doc.GetElement(fam.GetFamilySymbolIds().First()) as FamilySymbol; symbol.Activate(); try { File.Delete(tempMassFamilyPath); } catch { } var mass = Doc.Create.NewFamilyInstance(XYZ.Zero, symbol, DB.Structure.StructuralType.NonStructural); // NOTE: must set a schedule level! // otherwise the wall creation will fail with "Could not create a face wall." var level = new FilteredElementCollector(Doc) .WhereElementIsNotElementType() .OfCategory(BuiltInCategory.OST_Levels) // this throws a null error if user tries to recieve stream in a file with no levels .ToElements().FirstOrDefault(); if (level == null) // create a new level at 0 if no levels could be retrieved from doc { level = Level.Create(Doc, 0); } TrySetParam(mass, BuiltInParameter.INSTANCE_SCHEDULE_ONLY_LEVEL_PARAM, level); //must regenerate before getting the elem geometry Doc.Regenerate(); Reference faceRef = GetFaceRef(mass); var wallType = GetElementType <WallType>(speckleWall); if (!FaceWall.IsWallTypeValidForFaceWall(Doc, wallType.Id)) { ConversionErrors.Add(new Error { message = $"Wall type not valid for face wall ${speckleWall.applicationId}." }); return(null); } revitWall = null; try { revitWall = DB.FaceWall.Create(Doc, wallType.Id, GetWallLocationLine(speckleWall.locationLine), faceRef); } catch (Exception e) { } if (revitWall == null) { ConversionErrors.Add(new Error { message = $"Failed to create face wall ${speckleWall.applicationId}." }); return(null); } Doc.Delete(mass.Id); SetInstanceParameters(revitWall, speckleWall); var placeholders = new List <ApplicationPlaceholderObject>() { new ApplicationPlaceholderObject { applicationId = speckleWall.applicationId, ApplicationGeneratedId = revitWall.UniqueId, NativeObject = revitWall } }; var hostedElements = SetHostedElements(speckleWall, revitWall); placeholders.AddRange(hostedElements); return(placeholders); }