示例#1
0
        private RoomInfo Getinfo_Room(Document document, Room room)
        {
            if (room != null)

            {
                var info = new RoomInfo();
                info.Room       = room;
                info.RoomName   = room.Name;
                info.RoomLevel  = room.Level.Name;
                info.RoomNumber = room.Number;

                if (room.Location is LocationPoint location)
                {
                    XYZ point = location.Point;
                    info.RoomLocation = point;
                }

                #region GetHeight
                SpatialElementBoundaryOptions sebOptions = new SpatialElementBoundaryOptions
                {
                    SpatialElementBoundaryLocation = SpatialElementBoundaryLocation.Finish
                };
                SpatialElementGeometryCalculator calc    = new SpatialElementGeometryCalculator(document, sebOptions);
                SpatialElementGeometryResults    results = calc.CalculateSpatialElementGeometry(room);
                Solid roomSolid = results.GetGeometry();
                var   getbb     = roomSolid.GetBoundingBox();
                var   maxZ      = getbb.Max.Z;
                var   minZ      = getbb.Min.Z;
                info.RoomHeight = maxZ - minZ;
                #endregion

                IList <IList <BoundarySegment> > segments = room.GetBoundarySegments(new SpatialElementBoundaryOptions());

                if (null != segments)
                {
                    foreach (IList <BoundarySegment> segmentList in segments)
                    {
                        foreach (BoundarySegment boundarySegment in segmentList)
                        {
                            if (boundarySegment.GetCurve() is Line)
                            {
                                info.RoomBoundarySegment.Add(new RoomInfo
                                {
                                    RoomStartPoint = boundarySegment.GetCurve().GetEndPoint(0),
                                    RoomEndPoint   = boundarySegment.GetCurve().GetEndPoint(1)
                                });
                            }
                            if (boundarySegment.GetCurve() is Arc)
                            {
                                TaskDialog.Show("s", boundarySegment.GetCurve().GetType().ToString());
                            }
                        }
                    }
                }

                return(info);
            }

            return(null);
        }
示例#2
0
 private bool CreateRoomMass(SpatialElement room)
 {
     if (!SpatialElementGeometryCalculator.CanCalculateGeometry(room))
     {
         return(false);
     }
     try
     {
         SpatialElementGeometryResults results;
         using (var calculator = new SpatialElementGeometryCalculator(doc))
         {
             results = calculator.CalculateSpatialElementGeometry(room);
         }
         using (Solid roomSolid = results.GetGeometry())
         {
             var         eid       = new ElementId(BuiltInCategory.OST_Mass);
             DirectShape roomShape = DirectShape.CreateElement(doc, eid);
             if (roomShape != null && roomSolid.Volume > 0 && roomSolid.Faces.Size > 0)
             {
                 var geomObj = new GeometryObject[] { roomSolid };
                 if (geomObj.Length > 0)
                 {
                     roomShape.SetShape(geomObj);
                     CopyAllRoomParametersToMasses(room, roomShape);
                     return(true);
                 }
             }
         }
     }
     catch (Exception ex)
     {
         System.Diagnostics.Debug.WriteLine(ex.Message);
     }
     return(false);
 }
示例#3
0
        /// <summary>
        ///     Gets intersect element list.
        /// </summary>
        /// <param name="room"></param>
        /// <param name="doc"></param>
        /// <returns></returns>
        public static List <Element> GetIntersectElements(this SpatialElement room, Document doc)
        {
            if (room is null)
            {
                throw new ArgumentNullException(nameof(room));
            }

            if (doc is null)
            {
                throw new ArgumentNullException(nameof(doc));
            }

            var opt = new SpatialElementBoundaryOptions  {
                SpatialElementBoundaryLocation = Center
            };

            var calc = new SpatialElementGeometryCalculator(doc, opt);

            var solid = calc.CalculateSpatialElementGeometry(room).GetGeometry();

            var instFilter = new FilteredElementCollector(doc).WhereElementIsNotElementType();

            var itstFilter = new ElementIntersectsSolidFilter(solid);

            return(instFilter.WherePasses(itstFilter).ToList());
        }
 /// <summary>
 /// Destroys SpatialElementGeometryCalculator object.
 /// </summary>
 public static void DestroySpatialElementGeometryCalculator()
 {
    if (s_SpatialElementGeometryCalculator != null)
    {
       s_SpatialElementGeometryCalculator.Dispose();
       s_SpatialElementGeometryCalculator = null;
    }
 }
示例#5
0
        /// <summary>
        /// 使用空间计算工具计算房间Solid
        /// </summary>
        /// <param name="room"></param>
        /// <returns></returns>
        /// <remarks>轮廓上没问题,在高度上可能会出错</remarks>
        public static Solid GetRoomSolid(this Room room)
        {
            var bndOpt = new SpatialElementBoundaryOptions();
            SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(room.Document, bndOpt);
            SpatialElementGeometryResults    results    = calculator.CalculateSpatialElementGeometry(room); // compute the room geometry
            Solid roomSolid = results.GetGeometry();                                                        // get the solid representing the room's geometry

            return(roomSolid);
        }
示例#6
0
        public void Draw()
        {
            sortedlocalsTech = sortedlocalsTech.Distinct(new CusComparer()).ToList();
            try
            {
                for (int i = 0; i < sortedlocalsTech.Count(); i += 1)
                {
                    foreach (var item in sortedlocalsTech.ElementAt(i))
                    {
                        var myspace = doc.GetElement(item.Id) as Space;
                        SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(doc);
                        SpatialElementGeometryResults    results    = calculator.CalculateSpatialElementGeometry(myspace); // compute the room geometry
                        Solid roomSolid = results.GetGeometry();
                        results.GetGeometry();

                        XYZ sp = null, ep = null;

                        ElementId levelId  = ElementId.InvalidElementId;
                        Document  document = uidoc.Document;
                        Utils.lazyInstance.GetElementLocation(out sp, myspace);
                        BoundingBoxXYZ bbxyz = myspace.get_BoundingBox(null);

                        bbxyz.Enabled = true;
                        List <XYZ> edges = new List <XYZ>();
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(0).X, 2), Math.Round(bbxyz.get_Bounds(0).Y, 2), Math.Round(bbxyz.get_Bounds(1).Z, 2)));
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(1).X, 2), Math.Round(bbxyz.get_Bounds(0).Y, 2), Math.Round(bbxyz.get_Bounds(1).Z, 2)));
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(0).X, 2), Math.Round(bbxyz.get_Bounds(0).Y, 2), Math.Round(bbxyz.get_Bounds(0).Z, 2)));
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(1).X, 2), Math.Round(bbxyz.get_Bounds(0).Y, 2), Math.Round(bbxyz.get_Bounds(0).Z, 2)));
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(0).X, 2), Math.Round(bbxyz.get_Bounds(1).Y, 2), Math.Round(bbxyz.get_Bounds(1).Z, 2)));
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(1).X, 2), Math.Round(bbxyz.get_Bounds(1).Y, 2), Math.Round(bbxyz.get_Bounds(1).Z, 2)));
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(0).X, 2), Math.Round(bbxyz.get_Bounds(1).Y, 2), Math.Round(bbxyz.get_Bounds(0).Z, 2)));
                        edges.Add(new XYZ(Math.Round(bbxyz.get_Bounds(1).X, 2), Math.Round(bbxyz.get_Bounds(1).Y, 2), Math.Round(bbxyz.get_Bounds(0).Z, 2)));

                        Utils.lazyInstance.GetLowestAndHighestPolygon(edges, myspace.Level);
                        RevitDataContext.lazyInstance.SpacesInfo.Add(myspace, new Tuple <XYZ,
                                                                                         List <XYZ>,
                                                                                         List <XYZ>,
                                                                                         List <XYZ> >(Utils.lazyInstance.GetCenterOfPolygon(edges),
                                                                                                      edges, new List <XYZ>(Utils.lazyInstance.lowestPolyg), new List <XYZ>(Utils.lazyInstance.highestPolyg)));
                        ep = sp;
                    }
                    Debug.WriteLine("count(): " + RevitDataContext.lazyInstance.SpacesInfo.Count());
                    CreateDucts(i);
                    correspSmallestSpaces.Clear();
                    tiltingSpaces.Clear();
                    currentConnectors.Clear();
                    CorrespIntersec.Clear();
                    RevitDataContext.lazyInstance.SpacesInfo.Clear();
                }
            }
            catch
            {
                TaskDialog.Show("Erreur", "Erreur: Vérifier bien que toutes les gaines ont été correctement assigné. Supprimez tous les espaces non assignés et non clos.");
            }
        }
示例#7
0
        public static List <Panel> Panels(this SpatialElement spatialElement, SpatialElementBoundaryOptions spatialElementBoundaryOptions, Core.Revit.ConvertSettings convertSettings)
        {
            if (spatialElement == null || spatialElementBoundaryOptions == null)
            {
                return(null);
            }

            SpatialElementGeometryCalculator spatialElementGeometryCalculator = new SpatialElementGeometryCalculator(spatialElement.Document, spatialElementBoundaryOptions);

            return(Panels(spatialElement, spatialElementGeometryCalculator, convertSettings));
        }
示例#8
0
        /***************************************************/

        public static Space SpaceFromRevit(this SpatialElement spatialElement, SpatialElementBoundaryOptions spatialElementBoundaryOptions, RevitSettings settings = null, Dictionary <string, List <IBHoMObject> > refObjects = null)
        {
            if (spatialElement == null || spatialElementBoundaryOptions == null)
            {
                return(new Space());
            }

            SpatialElementGeometryCalculator spatialElementGeometryCalculator = new SpatialElementGeometryCalculator(spatialElement.Document, spatialElementBoundaryOptions);

            return(SpaceFromRevit(spatialElement, spatialElementGeometryCalculator, settings, refObjects));
        }
示例#9
0
        public double CalculateFamilyInstanceBBRadius()
        {
            BoundingBoxXYZ familySolidBB = null;

            using (Transaction tx = new Transaction(m_doc))
            {
                tx.Start("Transaction Temp");

                // Get a bottom face from room solid
                SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(m_doc);
                SpatialElementGeometryResults    results    = calculator.CalculateSpatialElementGeometry(m_room);
                Solid      roomSolid = results.GetGeometry();
                PlanarFace roomFace  = GetBottomPlanarFaceFromSolid(roomSolid);

                // Create family instance temporarily
                FamilyInstance tempInstance = m_doc.Create.NewFamilyInstance(roomFace.Origin, m_familySymbol, m_level, Autodesk.Revit.DB.Structure.StructuralType.NonStructural);

                // Get a boudingbox of family instance
                Options getometryOptions = new Options();
                getometryOptions.IncludeNonVisibleObjects = false;
                getometryOptions.View = m_view;

                GeometryElement geoElem = tempInstance.get_Geometry(getometryOptions);

                foreach (GeometryObject geoObject in geoElem)
                {
                    GeometryInstance geoInst = geoObject as GeometryInstance;

                    foreach (GeometryObject instanceGeoObject in geoInst.GetInstanceGeometry())
                    {
                        if (instanceGeoObject is Solid)
                        {
                            Solid solid = (Solid)instanceGeoObject;

                            familySolidBB = solid.GetBoundingBox();
                        }
                    }
                }

                tx.RollBack();
            }

            // Calculate perimeter of family instance
            XYZ familySolidBBMaxPt = familySolidBB.Max;
            XYZ familySolidBBMinPt = familySolidBB.Min;

            XYZ    minPt = new XYZ(familySolidBBMinPt.X, familySolidBBMinPt.Y, 0.0);
            XYZ    maxPt = new XYZ(familySolidBBMaxPt.X, familySolidBBMaxPt.Y, 0.0);
            double familySolidBBRadius = (minPt.DistanceTo(maxPt)) / 2;

            familySolidBBRadius = Math.Round(familySolidBBRadius, 4, MidpointRounding.AwayFromZero);

            return(familySolidBBRadius);
        }
示例#10
0
        public static void MoveRoomToCentroid(Document doc, List <Room> modelRooms)
        {
            SpatialElementGeometryCalculator geomCalculator = new SpatialElementGeometryCalculator(doc);
            bool NotEnclosedRooms = false;  //declare variable to detect Not Enclosed rooms

            foreach (Room r in modelRooms)
            {
                if (r.Area == 0) //are there not enclosed rooms?
                {
                    NotEnclosedRooms = true;
                    continue;
                }
                if (r.Area > 0) //hadle exception for Not Enclosed rooms when trying to calculate SpatialElementGeometry
                {
                    Location      rLoc            = r.Location;
                    LocationPoint currentLoc      = (LocationPoint)r.Location;
                    XYZ           currentLocPoint = currentLoc.Point;

                    SpatialElementGeometryResults geomResults = geomCalculator.CalculateSpatialElementGeometry(r);
                    Solid roomSolid    = geomResults.GetGeometry();
                    XYZ   roomCentroid = roomSolid.ComputeCentroid();

                    XYZ moveVector = new XYZ(roomCentroid.X - currentLocPoint.X, roomCentroid.Y - currentLocPoint.Y, roomCentroid.Z - currentLocPoint.Z);

                    // don´t move if centroid is outside of a room
                    if (r.IsPointInRoom(roomCentroid))
                    {
                        rLoc.Move(moveVector);
                    }
                }
            }

            if (NotEnclosedRooms == true)   //warn the user about not enclosed rooms
            {
                Form.Form_Main.warningMsgMain = "Warning";
                Form.Form_Main.warningMsgBody = string.Format("There are 'Not Enclosed' rooms in this project.{0}{0}" +
                                                              " This application have ignored them," +
                                                              " but I strongly recommend you to revise them and amend as appropriate."
                                                              , Environment.NewLine);

                using (UI.Info.Form_Warning thisForm = new UI.Info.Form_Warning())
                {
                    thisForm.ShowDialog();
                }
            }
        }
示例#11
0
        public Elements.Element[] FromRevit(Autodesk.Revit.DB.Element revitElement, Document document)
        {
            var geomCalculator = new SpatialElementGeometryCalculator(document);
            var space          = revitElement as Autodesk.Revit.DB.Mechanical.Space;
            var results        = geomCalculator.CalculateSpatialElementGeometry(space);
            var geometry       = results.GetGeometry();

            var spaceHeight = Elements.Units.FeetToMeters(space.get_BoundingBox(null).Max.Z - space.get_BoundingBox(null).Min.Z);

            var downfaces = geometry.GetMostLikelyHorizontalFaces(downwardFacing: true);

            var allRooms = new List <Room>();

            foreach (var face in downfaces)
            {
                foreach (var profile in face.GetProfiles(true))
                {
                    var room = new Room(profile.Perimeter, Vector3.ZAxis, "", "", "", "", 0, 0, 0, 0, spaceHeight, 0, null, Room.RoomMaterial, null, false, Guid.NewGuid(), "");
                    allRooms.Add(room);
                }
            }

            return(allRooms.ToArray());
        }
示例#12
0
        /// <summary>
        /// Creates the element in the model
        /// </summary>
        /// <param name="doc"></param>
        public void CreateLocal(StreamMessage message)
        {
            //insert at position?
            //find space it's in?
            //find family symbol/type?
            _dispatcher.QueueAction((uiapp) =>
            {
                var doc = uiapp.ActiveUIDocument.Document;

                var node        = message.After.AsNode();
                var nodeElement = doc.GetElement(node.Id);

                using (var updatetx = new Transaction(doc, "Update from stream"))
                {
                    updatetx.Start("Update from stream");

                    if (node.Labels.Contains("FanCoilUnit"))
                    {
                        if (nodeElement == null)
                        {
                            //create node
                            //
                            //get the space it's in

                            var query = @"
query($fcuid:ID!){
 FanCoilUnit (Id:$fcuid){
   Id
   ModelElements{
      Id
      UniqueId
     }
   Space{
        Id
     }
    ConnectedTo{
      Id
      Apparent_Load
      ModelElements{
       Id
       UniqueId
     }
    }
   }
}";
                            var vars  = new Dictionary <string, object>();
                            vars.Add("fcuid", node.Id);

                            var res = _client.ExecuteQuery(query, vars);

                            if (res.FanCoilUnit != null)
                            {
                                var fcu          = res.FanCoilUnit[0];
                                Element modelElm = null;
                                foreach (var modelelemet in fcu.ModelElements)
                                {
                                    var id   = modelelemet.UniqueId.Value;
                                    modelElm = doc.GetElement((string)id);
                                    if (modelElm != null)
                                    {
                                        break;
                                    }
                                }

                                if (fcu.Space != null)
                                {
                                    var spaceId = fcu.Space.Id.Value;

                                    //find space
                                    var spaceElm = doc.GetElement((string)spaceId) as SpatialElement;
                                    if (spaceElm != null)
                                    {
                                        //find center
                                        MEPRevitNode rv = new MEPRevitNode(spaceElm);

                                        var sbopt = new SpatialElementBoundaryOptions();
                                        sbopt.SpatialElementBoundaryLocation = SpatialElementBoundaryLocation.Finish;
                                        sbopt.StoreFreeBoundaryFaces         = true;
                                        SpatialElementGeometryCalculator sg  = new SpatialElementGeometryCalculator(doc, sbopt);
                                        var spgets = sg.CalculateSpatialElementGeometry(spaceElm);

                                        var spgeo        = spgets.GetGeometry();
                                        var center       = spgeo.ComputeCentroid();
                                        var bbox         = spgeo.GetBoundingBox();
                                        var heightOfUnit = 1;
                                        var randomOffset = (bbox.Max.X - bbox.Min.X) / 2 * (new Random().NextDouble() - 0.5);
                                        var inspoint     = new XYZ(center.X + randomOffset, center.Y, bbox.Max.Z - heightOfUnit);


                                        FilteredElementCollector famFilter = new FilteredElementCollector(doc);

                                        //this is static for this example. We will need to discover the type and pull the family
                                        //from a family library service.
                                        string familyName = "HL_FanCoilUnit_HotandChilledWaterSoffit3HorizontalRoundConnections";

                                        Family foundFam = famFilter.OfClass(typeof(Family)).ToElements().OfType <Family>().FirstOrDefault(fm => fm.Name == familyName);
                                        var fcuSymbol   = doc.GetElement(foundFam.GetFamilySymbolIds().FirstOrDefault()) as FamilySymbol;

                                        var newElm = doc.Create.NewFamilyInstance(inspoint, fcuSymbol, Autodesk.Revit.DB.Structure.StructuralType.NonStructural);


                                        //var props = MEPGraphUtils.GetNodePropsWithElementProps(new Client.Model.ModelElement(), newElm);
                                        //var newnode = _client.Push("ModelElement", props);
                                        //_client.Relate(new PendingNode(node), newnode, Client.Model.MEPEdgeTypes.REALIZED_BY, null);



                                        var nodeparamers = node.ExtendedProperties;
                                        foreach (var param in newElm.Parameters.OfType <Parameter>())
                                        {
                                            if (param.IsReadOnly)
                                            {
                                                continue;
                                            }

                                            var hp        = new HLRevitParameter(param);
                                            var paramName = Utils.GetGraphQLCompatibleFieldName(param.Definition.Name);

                                            if (nodeparamers.ContainsKey(paramName))
                                            {
                                                var incommingValue = nodeparamers[paramName];
                                                var currentValue   = MEPGraphUtils.RevitToGraphValue(hp);

                                                if (incommingValue != currentValue)
                                                {
                                                    hp.Value = incommingValue;
                                                }
                                            }
                                        }

                                        if (fcu.ConnectedTo != null)
                                        {
                                            string fcuName = "FCU";

                                            Family foundfcuFam = famFilter.OfClass(typeof(Family)).ToElements().OfType <Family>().FirstOrDefault(fm => fm.Name == fcuName);
                                            var fcueSymbol     = doc.GetElement(foundFam.GetFamilySymbolIds().FirstOrDefault()) as FamilySymbol;
                                            var fcuEinspt      = inspoint + new XYZ(1, 0, 0);
                                            var newFuceElm     = doc.Create.NewFamilyInstance(fcuEinspt, fcuSymbol, Autodesk.Revit.DB.Structure.StructuralType.NonStructural);


                                            foreach (var param in newFuceElm.Parameters.OfType <Parameter>())
                                            {
                                                if (param.IsReadOnly)
                                                {
                                                    continue;
                                                }

                                                var hp        = new HLRevitParameter(param);
                                                var paramName = Utils.GetGraphQLCompatibleFieldName(param.Definition.Name);

                                                if (fcu.ConnectedTo[paramName] != null)
                                                {
                                                    var incommingValue = fcu.ConnectedTo[paramName].Value;
                                                    var currentValue   = MEPGraphUtils.RevitToGraphValue(hp);

                                                    if (incommingValue != currentValue)
                                                    {
                                                        hp.Value = incommingValue;
                                                    }
                                                }
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }

                    updatetx.Commit();
                }
            });
        }
示例#13
0
        /// <summary>
        /// Test whether each room has a roof to bound it.
        /// </summary>
        /// <param name="message">Error message to be dumped.</param>
        /// <param name="elements">Some elements to return.</param>
        /// <returns></returns>
        private bool FindRoomBoundingRoofs(ref string message, Autodesk.Revit.DB.ElementSet elements)
        {
            // Get all rooms
            List <Element> rooms = GetRoomsElements();

            if (rooms.Count == 0)
            {
                message = "Unable to identify any rooms, please create room first!";
                return(false);
            }

            // Represents the criteria for boundary elements to be considered bounding roofs
            LogicalOrFilter categoryFilter = new LogicalOrFilter(new ElementCategoryFilter(BuiltInCategory.OST_Roofs),
                                                                 new ElementCategoryFilter(BuiltInCategory.OST_RoofSoffit));

            // Calculator for room/space geometry.
            SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(m_document);

            // Stores the resulting room->roof relationships
            Dictionary <Element, List <ElementId> > roomsAndRoofs = new Dictionary <Element, List <ElementId> >();

            foreach (Element room in rooms)
            {
                // Get room geometry & boundaries
                SpatialElementGeometryResults results = calculator.CalculateSpatialElementGeometry((SpatialElement)room);

                // Get solid geometry so we can examine each face
                Solid geometry = results.GetGeometry();

                foreach (Face face in geometry.Faces)
                {
                    // Get list of roof boundary subfaces for a given face
                    IList <SpatialElementBoundarySubface> boundaryFaces = results.GetBoundaryFaceInfo(face);
                    foreach (SpatialElementBoundarySubface boundaryFace in boundaryFaces)
                    {
                        // Get boundary element
                        LinkElementId boundaryElementId = boundaryFace.SpatialBoundaryElement;

                        // Only considering local file room bounding elements
                        ElementId localElementId = boundaryElementId.HostElementId;

                        // Evaluate if element meets criteria using PassesFilter()
                        if (localElementId != ElementId.InvalidElementId && categoryFilter.PassesFilter(m_document, localElementId))
                        {
                            // Room already has roofs, add more
                            if (roomsAndRoofs.ContainsKey(room))
                            {
                                List <ElementId> roofs = roomsAndRoofs[room];
                                if (!roofs.Contains(localElementId))
                                {
                                    roofs.Add(localElementId);
                                }
                            }
                            // Room found first roof
                            else
                            {
                                List <ElementId> roofs = new List <ElementId>();
                                roofs.Add(localElementId);
                                roomsAndRoofs.Add(room, roofs);
                            }
                            break;
                        }
                    }
                }
            }

            // Format results
            if (roomsAndRoofs.Count > 0)
            {
                String logs = String.Format("Rooms that have a bounding roof:");
                message += logs + "\t\r\n";
                Trace.WriteLine(logs);
                foreach (KeyValuePair <Element, List <ElementId> > kvp in roomsAndRoofs)
                {
                    // remove this room from all rooms list
                    rooms.Remove(kvp.Key);

                    List <ElementId> roofs = kvp.Value;
                    String           roofsString;

                    // Single roof boundary
                    if (roofs.Count == 1)
                    {
                        Element roof = m_document.GetElement(roofs[0]);
                        roofsString = String.Format("Roof: Id = {0}, Name = {1}", roof.Id.IntegerValue, roof.Name);
                    }
                    // Multiple roofs
                    else
                    {
                        roofsString = "Roofs ids = " + string.Join(", ", Array.ConvertAll <ElementId, string>(roofs.ToArray(), i => i.ToString()));
                    }

                    // Save results
                    logs = String.Format(
                        "  Room: Id = {0}, Name = {1} --> {2}",
                        kvp.Key.Id.IntegerValue, kvp.Key.Name, roofsString);
                    message += logs + "\t\r\n";
                    Trace.WriteLine(logs);
                }
            }

            // Format the rooms that have no bounding roof
            Trace.WriteLine("Geometry relationship checking finished...");
            if (rooms.Count != 0)
            {
                String logs = String.Format("Below rooms don't have bounding roofs:");
                message += logs + "\t\r\n";
                Trace.WriteLine(logs);
                foreach (Element room in rooms)
                {
                    elements.Insert(room);
                    logs = String.Format("  Room Id: {0}, Room Name: {1}",
                                         room.Id.IntegerValue, room.Name);
                    message += logs + "\t\r\n";
                    Trace.WriteLine(logs);
                }
            }

            return(true);
        }
示例#14
0
        public void ParseFrom(Element elm, MEPRevitGraphWriter writer)
        {
            var space = elm as Autodesk.Revit.DB.Mechanical.Space;

            if (space == null)
            {
                return;
            }

            if (space.Volume < 0.5)
            {
                return;
            }

            var scannedElements = writer.Cache.ParsedElements;
            var cpTree          = writer.Cache.connectorsCache;
            var geoTree         = writer.Cache.geoCache;
            var maxDepth        = writer.Cache.MaxDepth;
            var graph           = writer.Graph;

            var lvl = space.Level;

            if (lvl != null)
            {
                graph.AddConnection(elm, lvl, MEPPathConnectionType.Proximity, MEPEdgeTypes.IS_ON);
            }

            //get elements in the space


            //get areas with edges and add to walls

            var sbopt = new SpatialElementBoundaryOptions();

            sbopt.SpatialElementBoundaryLocation = SpatialElementBoundaryLocation.Finish;
            sbopt.StoreFreeBoundaryFaces         = true;

            //var geoOpt = new Options();
            //var spgeo = space.get_Geometry(geoOpt);

            //get nearby spaces by extending bb of space
            //foreach each face of space geometry
            //split into uv gripd
            //construct line from each point
            //get intersect with faces on nearby faces
            //if it hits increment area count for direction

            var doc = space.Document;
            SpatialElementGeometryCalculator sg = new SpatialElementGeometryCalculator(doc, sbopt);
            var spgets = sg.CalculateSpatialElementGeometry(space);
            var spgeo  = spgets.GetGeometry();
            //var spbb = spgeo.GetBoundingBox();
            var spbb = elm.get_BoundingBox(null);

            //var spbbhl = new HLBoundingBoxXYZ(spbb);
            //spbbhl.Size = spbbhl.Size + new XYZ(2, 2, 4);


            //get faces
            var uvdensity   = 0.75;
            var maxDistance = 4D;
            //var nearbyFaces = nearbySpaces.OfType<SolidGeometrySegment>().Where(spc => spc.OriginatingElement != space.Id).SelectMany(sp => sp.Geometry.Faces.OfType<Face>());

            var rayIncidents = new HashSet <FaceIntersectRay>();


            //get all the faces in the geometry
            var spfaces = spgeo.Faces.OfType <Face>().ToList();

            foreach (var gface in spfaces)
            {
                //extract the faces which bound with other elements (Walls, floors, ceilings, windows etc)
                var sfaceInfos = spgets.GetBoundaryFaceInfo(gface);
                foreach (var sfaceInfo in sfaceInfos)
                {
                    //get the geo face and element of this bounding face
                    var sface = sfaceInfo.GetSubface();

                    var elmId = sfaceInfo.SpatialBoundaryElement;

                    var lelm     = GetElementFromLinkedElement(elmId, doc);
                    var docIdent = string.Empty;
                    //if (lelm == null) continue; //ignore this face if it doesn't resolve to a valid element

                    //find the bounding uv box so we can work out a grid of points
                    var fbb  = sface.GetBoundingBox();
                    var uExt = uvdensity; // (fbb.Max.U - fbb.Min.U) / uvdensity;
                    var vExt = uvdensity; // (fbb.Max.V - fbb.Min.V) / uvdensity;

                    var u = fbb.Min.U;
                    var v = fbb.Min.V;

                    //var sb = new GeoLib.C2DPolygon();

                    //construct grid for ray tracing
                    Stack <UV> gridPoints = new Stack <UV>();
                    while (u <= fbb.Max.U)
                    {
                        v = fbb.Min.V;
                        while (v <= fbb.Max.V)
                        {
                            var uvp = new UV(u, v);
                            v += uvdensity;
                            if (!sface.IsInside(uvp))
                            {
                                continue;                       //only include points that are actually on this face
                            }
                            gridPoints.Push(uvp);
                        }
                        u += uvdensity;
                    }

                    var nerbyCheckCats         = new int[] { };
                    IList <ElementId> hostElms = new List <ElementId>();

                    if (lelm != null && !(lelm is HostObject))
                    {
                        var n = lelm;
                    }

                    if (lelm != null)
                    {
                        docIdent = DocUtils.GetDocumentIdent(lelm.Document);
                        //get cutting elemtns if it's a wall so we can find door and windows
                        if (lelm is HostObject)
                        {
                            var whost = lelm as HostObject;
                            hostElms = whost.FindInserts(true, true, true, true);
                            //build oct tree of hostelems so we can quickly ray trace them later
                            foreach (var hostElm in hostElms)
                            {
                                //ignoring any link and transform for now
                                var ehl = whost.Document.GetElement(hostElm);
                                writer.Cache.geoCacheWriter.AddElement(ehl, true);
                            }
                        }

                        //we need the nearby check to find the cut out elements
                        nerbyCheckCats = new int[] { (int)BuiltInCategory.OST_Doors, (int)BuiltInCategory.OST_Windows };
                    }
                    else
                    {
                        nerbyCheckCats = new int[] { (int)BuiltInCategory.OST_Doors, (int)BuiltInCategory.OST_Windows, (int)BuiltInCategory.OST_Floors, (int)BuiltInCategory.OST_Walls, (int)BuiltInCategory.OST_Roofs };

                        //we need the nearby check to find the bounding element
                        switch (sfaceInfo.SubfaceType)
                        {
                        case SubfaceType.Bottom:
                            nerbyCheckCats = new int[] { (int)BuiltInCategory.OST_Floors };
                            break;

                        case SubfaceType.Top:
                            nerbyCheckCats = new int[] { (int)BuiltInCategory.OST_Roofs, (int)BuiltInCategory.OST_Floors, (int)BuiltInCategory.OST_Windows };
                            break;

                        case SubfaceType.Side:
                            nerbyCheckCats = new int[] { (int)BuiltInCategory.OST_Doors, (int)BuiltInCategory.OST_Windows, (int)BuiltInCategory.OST_Walls };
                            break;
                        }
                    }

                    //option 1 - brute force ray trace
                    //option 2 - construct 2d polygon from edges of each face, translate each face into the same plane, then boolean intersect, get area of each intersect
                    //calc space boundaries at midpoint?
                    Face optLastIntermeidateFace = null;
                    SolidGeometrySegment optLastIntermeidateSegment = null;
                    Face optLastHitFace = null;
                    SolidGeometrySegment optLastHitSegment = null;
                    var arWeight = sface.Area / gridPoints.Count;
                    while (gridPoints.Count > 0)
                    {
                        var pt          = gridPoints.Pop();
                        var rayIncident = new FaceIntersectRay();

                        var nv = sface.ComputeNormal(pt).Normalize();
                        //var mx = sface.ComputeSecondDerivatives(pt).MixedDerivative.Normalize();
                        rayIncident.SourceElement = space;
                        rayIncident.SourceFace    = sface;
                        rayIncident.SourceUV      = pt;

                        rayIncident.RayVecotor          = nv;
                        rayIncident.IntermediatDocIdent = docIdent;
                        rayIncident.IntermeidateElement = lelm != null ? lelm.Id : ElementId.InvalidElementId;
                        rayIncident.AreaWeight          = arWeight;
                        rayIncident.SubFaceType         = sfaceInfo.SubfaceType;
                        rayIncidents.Add(rayIncident);

                        var sp = sface.Evaluate(pt);
                        rayIncident.SourceXYZ = sp;
                        var ray   = Line.CreateBound(sp, sp + nv * 4);
                        var rayBB = new HLBoundingBoxXYZ(sp, (sp + nv * 4), true);
                        //rayBB.Size = rayBB.Size + new XYZ(0.5, 0.5, 0.5);
                        //Plane geoPlane = Plane.c(sp, sp + nv * 5, sp + nv * 5 + (mx * 0.2));
                        //SketchPlane skPlane = SketchPlane.Create(doc, geoPlane);
                        //doc.Create.NewModelCurve(ray, skPlane);

                        //check cache for hit on otherside, if there is one nearby on this face we can ignore it as we're not including both sides
                        //var nearbyrayHits = writer.Cache.rayhitCache.GetNearby(ray, 0.4F);
                        //var validSimilarHit = nearbyrayHits.FirstOrDefault(rh => rh.HittingSegment != null && rh.HittingSegment.OriginatingElement == space.Id && rh.IntermeidateElement == rayIncident.IntermeidateElement);
                        //if (validSimilarHit != null && sface.IsInside(validSimilarHit.HittingUV))
                        //{
                        //    rayIncident.Ignore = true;
                        //    log.Info("Got hit on other side, ignoring");
                        //    continue;
                        // }

                        if (optLastIntermeidateFace != null)
                        {
                            IntersectionResultArray issRes = null;
                            var issGeoHit = getIntersect(pt, optLastIntermeidateFace, sface, maxDistance, out issRes, out double distance, nv, doc);
                            if (issGeoHit)
                            {
                                rayIncident.IntermediatDocIdent = optLastIntermeidateSegment.OriginatingDocIdent;
                                rayIncident.IntermeidateElement = optLastIntermeidateSegment.OriginatingElement;
                            }
                            else
                            {
                                optLastIntermeidateFace    = null;
                                optLastIntermeidateSegment = null;
                            }
                        }

                        GeometrySegment[] nearbyElements = null;

                        if (optLastIntermeidateFace == null)
                        {
                            nearbyElements = geoTree.GetColliding(rayBB);

                            var nearbyCutoutElements = nearbyElements.Where(iel =>
                                                                            (hostElms.Count == 0 || hostElms.Contains(iel.OriginatingElement)) &&
                                                                            nerbyCheckCats.Contains(iel.OriginatingElementCategory.IntegerValue))
                                                       .OfType <SolidGeometrySegment>();


                            IntersectionResultArray isRes = null;
                            bool isGeoHit = false;
                            foreach (var extSegment in nearbyCutoutElements)
                            {
                                foreach (var extFace in extSegment.Geometry.Faces.OfType <Face>())
                                {
                                    isGeoHit = getIntersect(pt, extFace, sface, maxDistance, out isRes, out double distance, nv, doc);
                                    if (isGeoHit)
                                    {
                                        rayIncident.IntermediatDocIdent = extSegment.OriginatingDocIdent;
                                        rayIncident.IntermeidateElement = extSegment.OriginatingElement;
                                        optLastIntermeidateFace         = extFace;
                                        optLastIntermeidateSegment      = extSegment;
                                        break;
                                    }
                                }
                                if (isGeoHit)
                                {
                                    break;
                                }
                            }
                        }



                        if (optLastHitFace != null)
                        {
                            var isHit = getIntersect(pt, optLastHitFace, sface, maxDistance, out var isRe, out double distance, nv, doc);
                            var isRes = isRe;
                            //project point onto other face instead?
                            var srcXYZ   = sface.Evaluate(pt);
                            var otXYZRes = optLastHitFace.Project(srcXYZ);

                            if (isHit)
                            {
                                var itx = isRes.OfType <IntersectionResult>().FirstOrDefault();
                                rayIncident.HittingFace    = optLastHitFace;
                                rayIncident.HittingSegment = optLastHitSegment;
                                rayIncident.HittingUV      = itx.UVPoint;
                                rayIncident.HittingXYZ     = itx.XYZPoint;
                                rayIncident.Distance       = distance;
                                nv = sface.ComputeNormal(pt).Normalize();
                                continue; //shortcut if we find a hit on the same face again
                            }
                            else
                            {
                                optLastHitFace    = null;
                                optLastHitSegment = null;
                            }
                        }


                        if (nearbyElements == null)
                        {
                            nearbyElements = geoTree.GetColliding(rayBB, (ob) => { return(ob.OriginatingElementCategory.IntegerValue == (int)BuiltInCategory.OST_MEPSpaces); });
                        }

                        //BoundingBoxIntersectsFilter bif = new BoundingBoxIntersectsFilter(new Outline(sp - new XYZ(0.1, 0.1, 0.1), (sp + nv * 2) + new XYZ(0.1, 0.1, 0.1)));
                        //var sfv = new FilteredElementCollector(space.Document);
                        //var sepl = sfv.WherePasses(bif).ToElements();

                        var nearbySpaces = nearbyElements.Where(ne => ne.OriginatingElementCategory.IntegerValue == (int)BuiltInCategory.OST_MEPSpaces).OfType <SolidGeometrySegment>().Distinct().ToList();

                        //find the extents of this face which face faces on other nearby faces (whaaat?)
                        //check each face of each nearby space for intersect with ray
                        foreach (var nearSpace in nearbySpaces)
                        {
                            var isHit = false;
                            foreach (var otFace in nearSpace.Geometry.Faces.OfType <Face>())
                            {
                                isHit = getIntersect(pt, otFace, sface, maxDistance, out var isRe, out double distance, nv, doc);
                                var isRes = isRe;
                                //project point onto other face instead?
                                var srcXYZ   = sface.Evaluate(pt);
                                var otXYZRes = otFace.Project(srcXYZ);

                                if (isHit)
                                {
                                    if (nearSpace.OriginatingElement.IntegerValue != elm.Id.IntegerValue)
                                    {
                                        var itx = isRes.OfType <IntersectionResult>().FirstOrDefault();
                                        rayIncident.HittingFace    = otFace;
                                        rayIncident.HittingSegment = nearSpace;
                                        rayIncident.HittingUV      = itx.UVPoint;
                                        rayIncident.HittingXYZ     = itx.XYZPoint;
                                        rayIncident.Distance       = distance;

                                        nv = sface.ComputeNormal(pt).Normalize();

                                        //optimization: check this face again first for the next ray check, since it's likely to be another hit
                                        optLastHitFace    = otFace;
                                        optLastHitSegment = nearSpace;

                                        rayIncident.Ignore = false;
                                    }
                                    else
                                    {
                                        if (distance < 0.1)
                                        {
                                            isHit = false;                 //looks like we hit our own face, ouch!
                                        }
                                        rayIncident.Ignore = true;
                                    }

                                    break;
                                }
                            }
                            if (isHit)
                            {
                                break;
                            }
                        }
                    }
                }

                /*
                 * space
                 * face
                 *    intermediate element (Wall/window/door)
                 *        face (space)
                 * face
                 *
                 *
                 * add connection
                 * this space -> section -> other space
                 * wall ------------^
                 */
            }

            //var ec = new elmComparer();
            var              srcNode        = graph.AddElement(space);
            double           minIncluedArea = 4;
            VectorBucketiser vbw            = new VectorBucketiser(8, 5);

            var includeRays = rayIncidents.Where(r => !r.Ignore);

            var outsideNode = graph.Nodes.FirstOrDefault(n => n.Name == "Outside");
            var groundNode  = graph.Nodes.FirstOrDefault(n => n.Name == "Ground");

            //group by the intermediate element (wall/floor/etc)
            foreach (var docGroup in includeRays.GroupBy(ri => ri.IntermediatDocIdent))//, ec))
            {
                var sdoc = DocUtils.GetDocument(docGroup.Key, elm.Document.Application);

                foreach (var intermediateElemGroup in docGroup.GroupBy(ri => ri.IntermeidateElement.IntegerValue))//, ec))
                {
                    var     selmid = new ElementId(intermediateElemGroup.Key);
                    Element selm   = sdoc != null?sdoc.GetElement(selmid) : null;

                    //group similar vectors into buckets
                    foreach (var rayVectorBuckets in intermediateElemGroup.GroupBy(ri => vbw.GetBucket(ri.RayVecotor)))
                    {
                        var rg = rayVectorBuckets.ToList();

                        var gs = rg.GroupBy(vr => vr.HittingSegment == null ? null : vr.HittingSegment.OriginatingElement).ToList();
                        //group each vector and intermediate element by the element it hits
                        foreach (var orgElmGroup in gs)
                        {
                            //find a section already matching this section
                            //actually easier to treat each path as separate sections
                            //var edNodes = graph.GetEdges(intermediateElemGroup.Key).Where(ed => ed.NextNode.AsAbstractNode.Name == "Surface"
                            //&& ed.NextNode.Connections.Any(cn => cn.NextNode.OriginId == spNode.OriginId)).Where(ed => ed.;

                            var apporxIntersect = orgElmGroup.Sum(et => et.AreaWeight);
                            var vector          = orgElmGroup.First().RayVecotor;
                            if (apporxIntersect < minIncluedArea)
                            {
                                continue;
                            }

                            var direction = VectorBucketiser.GetZeroClamppedPoint(orgElmGroup.First().RayVecotor); //should be rayVectorGroup.Key.AverageVector, but not yet implemented;

                            MEPRevitNode spNode = null;
                            if (orgElmGroup.Key != null)
                            {
                                var otherSpace = doc.GetElement(orgElmGroup.Key);
                                spNode = graph.AddElement(otherSpace);
                            }
                            else
                            {
                                if (selm != null && (selm.Name.ToLower().Contains("exterior") || selm is Autodesk.Revit.DB.Opening || selm.Name.ToLower().Contains("window") || selm is Autodesk.Revit.DB.RoofBase))
                                {
                                    if (outsideNode == null)
                                    {
                                        outsideNode = new MEPRevitNode("Outside", "Boundary", "OutsideBoundary", new MEPGraph.Model.Environment());
                                    }
                                    spNode = outsideNode;
                                }
                                else if (selm != null && (selm.Name.ToLower().Contains("floor") || selm is Autodesk.Revit.DB.Floor))
                                {
                                    if (groundNode == null)
                                    {
                                        groundNode = new MEPRevitNode("Ground", "Boundary", "GroundBoundary", new MEPGraph.Model.Environment());
                                    }
                                    spNode = groundNode;
                                }
                                else
                                {
                                    spNode = new MEPRevitNode("Void", "Boundary", "OtherBoundary", new MEPGraph.Model.VoidVolume());
                                    continue; //ignore void boundaries for now
                                }
                            }


                            var sectionN = graph.NewSection(selm, MEPGraph.Model.MEPEdgeTypes.IS_ON);

                            if (selm == null)
                            {
                                var emptyBondary = new MEPRevitNode();
                                emptyBondary.AsAbstractNode.Name = "OpenBoundary";
                                var cl = graph.AddConnection(emptyBondary, sectionN, MEPPathConnectionType.SectionOf, MEPGraph.Model.MEPEdgeTypes.IS_ON);
                                cl.AsNodeEdge.ExtendedProperties.Add("rvid", intermediateElemGroup.Key);
                            }

                            sectionN.AsAbstractNode.Name = "Surface";
                            var edgesf = graph.AddConnection(srcNode, sectionN, MEPPathConnectionType.Analytical, MEPGraph.Model.MEPEdgeTypes.BOUNDED_BY);

                            //total up intersecting area
                            var sampleIntersect = orgElmGroup.First();


                            edgesf.SetWeight("Area", apporxIntersect);
                            //edgesf.SetWeight("Direction", new HoareLea.MEPGraph.Model.MEPPoint(direction.X, direction.Y, direction.Z));
                            edgesf.SetWeight("DirectionX", direction.X);
                            edgesf.SetWeight("DirectionY", direction.Y);
                            edgesf.SetWeight("DirectionZ", direction.Z);
                            edgesf.SetWeight("SubFaceType", (int)sampleIntersect.SubFaceType);

                            /*
                             * HLBoundingBoxXYZ bb = new HLBoundingBoxXYZ();
                             * foreach (var et in orgElmGroup)
                             * {
                             *  if (et.HittingXYZ != null)
                             *  {
                             *      bb.ExpandToContain(et.HittingXYZ);
                             *  }
                             * }
                             * if (!bb.IsInvalid)
                             * {
                             *  sectionN.BoundingBox = bb;
                             *  var avgCenterPoint = bb.MidPoint;
                             *  var size = bb.Size;
                             *  sectionN.SetProperty("OriginX", avgCenterPoint.X);
                             *  sectionN.SetProperty("OriginY", avgCenterPoint.Y);
                             *  sectionN.SetProperty("OriginZ", avgCenterPoint.Z);
                             *  sectionN.SetProperty("SizeX", size.X);
                             *  sectionN.SetProperty("SizeY", size.Y);
                             *  sectionN.SetProperty("SizeZ", size.Z);
                             * }*/



                            var edgest     = graph.AddConnection(sectionN, spNode, MEPPathConnectionType.Analytical, MEPGraph.Model.MEPEdgeTypes.BOUNDED_BY);
                            var directionn = direction;//.Negate();
                            edgest.SetWeight("Area", apporxIntersect);
                            edgest.SetWeight("DirectionX", directionn.X);
                            edgest.SetWeight("DirectionY", directionn.Y);
                            edgest.SetWeight("DirectionZ", directionn.Z);
                            edgest.SetWeight("SubFaceType", (int)sampleIntersect.SubFaceType);
                        }
                    }
                }
            }
        }
 /// <summary>
 /// Initializes SpatialElementGeometryCalculator object.
 /// </summary>
 /// <param name="document">
 /// The Revit document.
 /// </param>
 /// <param name="exporterIFC">
 /// The ExporterIFC object.
 /// </param>
 public static void InitializeSpatialElementGeometryCalculator(Document document, ExporterIFC exporterIFC)
 {
     SpatialElementBoundaryOptions options = GetSpatialElementBoundaryOptions(null);
     s_SpatialElementGeometryCalculator = new SpatialElementGeometryCalculator(document, options);
 }
示例#16
0
        public static List <Panel> Panels(this SpatialElement spatialElement, SpatialElementGeometryCalculator spatialElementGeometryCalculator, Core.Revit.ConvertSettings convertSettings)
        {
            if (spatialElement == null || spatialElementGeometryCalculator == null)
            {
                return(null);
            }

            SpatialElementGeometryResults spatialElementGeometryResults = spatialElementGeometryCalculator.CalculateSpatialElementGeometry(spatialElement);

            if (spatialElementGeometryResults == null)
            {
                return(null);
            }

            Solid solid = spatialElementGeometryResults.GetGeometry();

            if (solid == null)
            {
                return(null);
            }

            List <Tuple <Face, LinkElementId, SubfaceType> > tuples = new List <Tuple <Face, LinkElementId, SubfaceType> >();

            foreach (Face face in solid.Faces)
            {
                IList <SpatialElementBoundarySubface> spatialElementBoundarySubfaces = spatialElementGeometryResults.GetBoundaryFaceInfo(face);
                if (spatialElementBoundarySubfaces == null || spatialElementBoundarySubfaces.Count == 0)
                {
                    tuples.Add(new Tuple <Face, LinkElementId, SubfaceType>(face, null, SubfaceType.Side));
                    continue;
                }

                foreach (SpatialElementBoundarySubface spatialElementBoundarySubface in spatialElementBoundarySubfaces)
                {
                    if (spatialElementBoundarySubface == null)
                    {
                        continue;
                    }

                    Face face_Subface = spatialElementBoundarySubface.GetSubface();
                    //Face face_Subface = spatialElementBoundarySubface.GetSpatialElementFace();
                    LinkElementId linkElementId = spatialElementBoundarySubface.SpatialBoundaryElement;

                    tuples.Add(new Tuple <Face, LinkElementId, SubfaceType>(face_Subface, linkElementId, spatialElementBoundarySubface.SubfaceType));
                }
            }

            List <Panel> result = new List <Panel>();

            foreach (Tuple <Face, LinkElementId, SubfaceType> tuple in tuples)
            {
                List <Geometry.Spatial.Face3D> face3Ds = Geometry.Revit.Convert.ToSAM(tuple.Item1);
                if (face3Ds == null || face3Ds.Count == 0)
                {
                    continue;
                }

                foreach (Geometry.Spatial.Face3D face3D in face3Ds)
                {
                    PanelType    panelType    = PanelType.Undefined;
                    Construction construction = null;
                    Panel        panel        = null;

                    if (tuple.Item2 != null)
                    {
                        Element element = Core.Revit.Query.Element(spatialElement.Document, tuple.Item2);
                        if (element != null)
                        {
                            HostObject hostObject = element as HostObject;
                            if (hostObject != null)
                            {
                                List <Panel> panels = hostObject.ToSAM(convertSettings);
                                if (panels != null && panels.Count > 0)
                                {
                                    panel = panels[0];
                                }

                                if (panel != null)
                                {
                                    construction = panel.Construction;
                                    panelType    = Analytical.Query.PanelType(construction?.Name);

                                    if (panelType == PanelType.Undefined)
                                    {
                                        panelType = panel.PanelType;
                                    }
                                }

                                if (panelType == PanelType.Undefined)
                                {
                                    panelType = Query.PanelType(hostObject);
                                }

                                if (construction == null)
                                {
                                    ElementId elementId_Type = hostObject.GetTypeId();
                                    if (elementId_Type != null && elementId_Type != ElementId.InvalidElementId)
                                    {
                                        construction = ((HostObjAttributes)hostObject.Document.GetElement(elementId_Type)).ToSAM(convertSettings);
                                    }
                                }
                            }
                        }
                    }

                    if (panelType == PanelType.Undefined)
                    {
                        panelType = Analytical.Query.PanelType(face3D.GetPlane()?.Normal);
                    }

                    if (panelType == PanelType.Undefined)
                    {
                        switch (tuple.Item3)
                        {
                        case SubfaceType.Bottom:
                            panelType = PanelType.Floor;
                            break;

                        case SubfaceType.Top:
                            panelType = PanelType.Roof;
                            break;

                        case SubfaceType.Side:
                            panelType = PanelType.Wall;
                            break;
                        }
                    }

                    if (construction == null)
                    {
                        construction = Analytical.Query.DefaultConstruction(panelType); //Default Construction
                    }
                    if (panel == null)
                    {
                        panel = Analytical.Create.Panel(construction, panelType, face3D);
                    }
                    else
                    {
                        panel = Analytical.Create.Panel(panel.Guid, panel, face3D);
                    }

                    result.Add(panel);
                }
            }

            return(result);
        }
示例#17
0
        public static Dictionary <ElementId, double> MaterialsAreas(this SpatialElement spatialElement, double minArea = 0, SpatialElementGeometryCalculator spatialElementGeometryCalculator = null)
        {
            if (spatialElement == null)
            {
                return(null);
            }

            if (double.IsNaN(spatialElement.Area) || spatialElement.Area < minArea)
            {
                return(null);
            }

            if (spatialElementGeometryCalculator == null)
            {
                SpatialElementBoundaryOptions spatialElementBoundaryOptions = new SpatialElementBoundaryOptions()
                {
                    SpatialElementBoundaryLocation = SpatialElementBoundaryLocation.Finish,
                    StoreFreeBoundaryFaces         = false
                };

                spatialElementGeometryCalculator = new SpatialElementGeometryCalculator(spatialElement.Document, spatialElementBoundaryOptions);
            }

            SpatialElementGeometryResults spatialElementGeometryResults = spatialElementGeometryCalculator.CalculateSpatialElementGeometry(spatialElement);

            if (spatialElementGeometryResults == null)
            {
                return(null);
            }

            Solid solid = spatialElementGeometryResults.GetGeometry();

            if (solid == null)
            {
                return(null);
            }

            Dictionary <ElementId, double> result = new Dictionary <ElementId, double>();

            foreach (Face face in solid.Faces)
            {
                if (face.Area < minArea)
                {
                    continue;
                }

                foreach (SpatialElementBoundarySubface spatialElementBoundarySubface in spatialElementGeometryResults.GetBoundaryFaceInfo(face))
                {
                    Face face_SpatialElement = spatialElementBoundarySubface.GetSpatialElementFace();
                    if (face_SpatialElement == null)
                    {
                        continue;
                    }

                    if (face_SpatialElement.Area < minArea)
                    {
                        continue;
                    }

                    Face face_BoundingElement = spatialElementBoundarySubface.GetBoundingElementFace();
                    if (face_BoundingElement == null)
                    {
                        continue;
                    }

                    ElementId elementId = face_BoundingElement.MaterialElementId;
                    if (elementId != null && elementId != Autodesk.Revit.DB.ElementId.InvalidElementId)
                    {
                        if (result.ContainsKey(elementId))
                        {
                            result[elementId] += face_SpatialElement.Area;
                        }
                        else
                        {
                            result[elementId] = face_SpatialElement.Area;
                        }
                    }
                }
            }

            return(result);
        }
        /// <summary>
        /// Collect relationship information from Ceiling to Room to be used later to determine whether a Ceiling can be contained in a Room
        /// </summary>
        /// <param name="spatialElement">The revit spatial object to process</param>
        /// <returns></returns>
        static private bool getCeilingSpaceBoundary(SpatialElement spatialElement)
        {
            // Represents the criteria for boundary elements to be considered bounding Ceiling
            LogicalOrFilter categoryFilter = new LogicalOrFilter(new ElementCategoryFilter(BuiltInCategory.OST_Ceilings),
                                                        new ElementCategoryFilter(BuiltInCategory.OST_Ceilings));

            SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(spatialElement.Document);
            SpatialElementGeometryResults results = calculator.CalculateSpatialElementGeometry((SpatialElement)spatialElement);
            Solid geometry = results.GetGeometry();

            // Go through the boundary faces to identify whether it is bounded by a Ceiling. If it is Ceiling, add into the Cache
            foreach (Face face in geometry.Faces)
            {
                IList<SpatialElementBoundarySubface> boundaryFaces = results.GetBoundaryFaceInfo(face);
                foreach (SpatialElementBoundarySubface boundaryFace in boundaryFaces)
                {
                    // Get boundary element
                    LinkElementId boundaryElementId = boundaryFace.SpatialBoundaryElement;

                    // Only considering local file room bounding elements
                    ElementId localElementId = boundaryElementId.HostElementId;
                    // Evaluate if element meets criteria using PassesFilter()
                    if (localElementId != ElementId.InvalidElementId && categoryFilter.PassesFilter(spatialElement.Document, localElementId))
                    {
                        if (ExporterCacheManager.CeilingSpaceRelCache.ContainsKey(localElementId))
                        {
                            // The ceiling already exists in the Dictionary, add the Space into list
                            IList<ElementId> roomlist = ExporterCacheManager.CeilingSpaceRelCache[localElementId];
                            roomlist.Add(spatialElement.Id);
                        }
                        else
                        {
                            // The first time this Ceiling Id appears
                            IList<ElementId> roomlist = new List<ElementId>();
                            roomlist.Add(spatialElement.Id);
                            ExporterCacheManager.CeilingSpaceRelCache.Add(localElementId, roomlist);
                        }

                    }
                }
            }

            return true;
        }
示例#19
0
        /***************************************************/

        public static Space SpaceFromRevit(this SpatialElement spatialElement, SpatialElementGeometryCalculator spatialElementGeometryCalculator, RevitSettings settings = null, Dictionary <string, List <IBHoMObject> > refObjects = null)
        {
            if (spatialElement == null || spatialElementGeometryCalculator == null)
            {
                return(new Space());
            }

            settings = settings.DefaultIfNull();

            Space space = refObjects.GetValue <Space>(spatialElement.Id);

            if (space != null)
            {
                return(space);
            }

            //Create the Space
            space      = new Space();
            space.Name = Query.Name(spatialElement);

            PolyCurve pcurve = spatialElement.Perimeter(settings).FirstOrDefault();

            if (pcurve != null)
            {
                space.Location  = pcurve.Centroid();
                space.Perimeter = pcurve;
            }
            else if (spatialElement.Location != null && spatialElement.Location is LocationPoint)
            {
                space.Location = ((LocationPoint)spatialElement.Location).FromRevit();
            }

            //Set ExtendedProperties
            OriginContextFragment originContext = new OriginContextFragment()
            {
                ElementID = spatialElement.Id.IntegerValue.ToString(), TypeName = Query.Name(spatialElement)
            };

            originContext.SetProperties(spatialElement, settings.ParameterSettings);
            space.AddFragment(originContext);

            SpaceAnalyticalFragment spaceAnalytical = new SpaceAnalyticalFragment();

            spaceAnalytical.SetProperties(spatialElement, settings.ParameterSettings);
            space.AddFragment(spaceAnalytical);

            SpaceContextFragment spaceContext = new SpaceContextFragment();

            spaceContext.SetProperties(spatialElement, settings.ParameterSettings);

            //TODO: Implement ConnectedElements
            space.AddFragment(spaceContext);

            //Set identifiers, parameters & custom data
            space.SetIdentifiers(spatialElement);
            space.CopyParameters(spatialElement, settings.ParameterSettings);
            space.SetProperties(spatialElement, settings.ParameterSettings);

            refObjects.AddOrReplace(spatialElement.Id, space);
            return(space);
        }
        // defines the Main Method with 1 argument: ActiveUIDoc
        public void SetRoomFinishingParameters(UIDocument ActiveUIDoc)
        {
            //Active document in Revit application
            Document doc = ActiveUIDoc.Document;

            //Get collection of Rooms in indicated level
            IEnumerable <Element> collector = FindRooms(ActiveUIDoc);

            //List of RoomData
            List <RoomData> roomDataList = new List <RoomData>();

            foreach (Room r in collector)
            {
                #region Retrieving of Room Data
                //List of RoomBoudingElements
                List <Element> roomBoundingElems = new List <Element>();

                // Calculate a room's geometry and find its boundary faces
                SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(doc);
                SpatialElementGeometryResults    results    = calculator.CalculateSpatialElementGeometry(r); // compute the room geometry
                Solid roomSolid = results.GetGeometry();                                                     // get the solid representing the room's geometry

                // Go through the boundary faces to add this element to the list of roomBoundingElems
                foreach (Face face in roomSolid.Faces)
                {
                    IList <SpatialElementBoundarySubface> boundaryFaces = results.GetBoundaryFaceInfo(face);
                    foreach (SpatialElementBoundarySubface boundaryFace in boundaryFaces)
                    {
                        // Get boundary element
                        LinkElementId boundaryElementId = boundaryFace.SpatialBoundaryElement;

                        // Only considering local file room bounding elements
                        ElementId localElementId = boundaryElementId.HostElementId;
                        Element   elem           = doc.GetElement(localElementId);

                        //Add Room Bounding Element to list
                        roomBoundingElems.Add(elem);
                    }
                }

                //List of all Element Types of the Room Bounding Elements
                List <Element> elemsType = new List <Element>();

                foreach (Element elem in roomBoundingElems)
                {
                    ElementId id       = elem.GetTypeId();
                    Element   elemType = doc.GetElement(id);
                    elemsType.Add(elemType);
                }

                //List of all unique Element Types of the Room Bounding Elements
                List <Element> elemsTypeDist = elemsType.Distinct(new ElemTypeIdEqualityComparer()).ToList();

                //List of all unique Element Types of the Room Bounding Elements with the Floors Assembly Code indicated
                IEnumerable <Element> finishingFloorsElemsTypes = GetFinishingElemsTypes(elemsTypeDist, finishingFloorsAssemblyCode);
                //Dictionary with Key values and Keynote Texts
                Dictionary <string, string> finishingFloorsKeynote = GetKeynote(finishingFloorsElemsTypes, ActiveUIDoc); //Dictionary<string, string>

                //List of all unique Element Types of the Room Bounding Elements with the Floors Assembly Code indicated
                IEnumerable <Element> finishingWallsElemsTypes = GetFinishingElemsTypes(elemsTypeDist, finishingWallsAssemblyCode);
                //Dictionary with Key values and Keynote Texts
                Dictionary <string, string> finishingWallsKeynote = GetKeynote(finishingWallsElemsTypes, ActiveUIDoc);

                //List of all unique Element Types of the Room Bounding Elements with the Floors Assembly Code indicated
                IEnumerable <Element> ceilingsElemsTypes = GetFinishingElemsTypes(elemsTypeDist, ceilingsAssemblyCode);
                //Dictionary with Key values and Keynote Texts
                Dictionary <string, string> ceilingsKeynote = GetKeynote(ceilingsElemsTypes, ActiveUIDoc);

                #endregion // Retrieving of Room Data

                //new RoomData class per room
                var RD = new RoomData
                {
                    room            = r,
                    elems           = roomBoundingElems,
                    finishingFloors = finishingFloorsKeynote,
                    finishingWalls  = finishingWallsKeynote,
                    ceilings        = ceilingsKeynote,
                };

                //Adds Room Data to Room Data List
                roomDataList.Add(RD);
            }

            //Fills Parameters
            FillParameters(roomDataList, doc);
        }
示例#21
0
        public static Result ExecuteCalculations(ExternalCommandData commandData)
        {
            UIApplication uiapp = commandData.Application;
            UIDocument    uidoc = uiapp.ActiveUIDocument;
            Application   app   = uiapp.Application;
            Document      doc   = uidoc.Document;

            List <string> roomNames     = new List <string>();
            List <string> areaType      = new List <string>();
            List <string> areaValue     = new List <string>();
            List <string> levelNames    = new List <string>();
            List <string> areaValueCalc = new List <string>();

            using (Transaction t = new Transaction(doc, "Turn on volume calculation"))
            {
                t.Start();
                AreaVolumeSettings settings = AreaVolumeSettings.GetAreaVolumeSettings(doc);
                settings.ComputeVolumes = true;
                t.Commit();
            }

            // setup spacial properties
            SpatialElementBoundaryOptions sebOptions = new SpatialElementBoundaryOptions();



            // get all rooms
            FilteredElementCollector room_collector = new FilteredElementCollector(doc).OfCategory(BuiltInCategory.OST_Rooms).WhereElementIsNotElementType();
            IList <ElementId>        room_eids      = room_collector.ToElementIds() as IList <ElementId>;

            foreach (ElementId eid in room_eids)
            {
                Room room = doc.GetElement(eid) as Room;
                {
                    // grab room spacial calculations
                    sebOptions.SpatialElementBoundaryLocation = SpatialElementBoundaryLocation.Center;
                    SpatialElementGeometryCalculator centerCalc = new SpatialElementGeometryCalculator(doc, sebOptions);
                    SpatialElementGeometryResults    center     = centerCalc.CalculateSpatialElementGeometry(room);

                    sebOptions.SpatialElementBoundaryLocation = SpatialElementBoundaryLocation.Finish;
                    SpatialElementGeometryCalculator finishCalc = new SpatialElementGeometryCalculator(doc, sebOptions);
                    SpatialElementGeometryResults    finish     = finishCalc.CalculateSpatialElementGeometry(room);

                    // get room properties
                    roomNames.Add(room.Name);
                    areaType.Add("Center");
                    levelNames.Add(room.Level.Name);
                    areaValue.Add(center.GetGeometry().SurfaceArea.ToString());

                    TaskDialog.Show("Revit", room.Name + room.Level.Name + center.GetGeometry().SurfaceArea.ToString());


                    roomNames.Add(room.Name);
                    areaType.Add("Finish");
                    levelNames.Add(room.Level.Name);
                    areaValue.Add(finish.GetGeometry().SurfaceArea.ToString());

                    TaskDialog.Show("Revit", room.Name + room.Level.Name + finish.GetGeometry().SurfaceArea.ToString());
                }
            }



            return(Result.Succeeded);
        }
示例#22
0
        public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)
        {
            UIApplication uiapp = commandData.Application;
            UIDocument    uidoc = uiapp.ActiveUIDocument;
            Document      doc   = uidoc.Document;
            Selection     sel   = uidoc.Selection;

            var collector = new FilteredElementCollector(doc);

            //var rooms = collector.OfClass(typeof(Room));

            //var phases = doc.Phases;
            //foreach (Phase phase in phases)
            //{
            //    MessageBox.Show(phase.Name.ToString());
            //}

            if (!(doc.ActiveView is ViewPlan))
            {
                MessageBox.Show("请转到平面视图");
                return(Result.Cancelled);
            }
            //创建房间(根据墙围成的闭合图形生成房间)
            var rooms = new List <SpatialElement>();

            doc.Invoke(m =>
            {
                Createrooms(doc, doc.ActiveView.GenLevel, doc.Phases.get_Item(1));
            }, "当前视图楼层创建房间");
            //下一步用创建的房间进行标高分析
            rooms = doc.TCollector <SpatialElement>().ToList();
            MessageBox.Show(rooms.Count.ToString());

            var names = rooms.Select(m => m.Name);

            var namestring = string.Join("\n", names);

            MessageBox.Show(namestring);

            var geometrys = new List <GeometryObject>();

            foreach (SpatialElement spatialElement in rooms)
            {
                var geometry = default(GeometryObject);

                if (SpatialElementGeometryCalculator.IsRoomOrSpace(spatialElement))
                {
                    MessageBox.Show(spatialElement.Name + "is roomOrSpace");
                }
                else
                {
                    MessageBox.Show(spatialElement.Name + "is not roomOrSpace");
                }

                try
                {
                    geometry = new SpatialElementGeometryCalculator(doc).CalculateSpatialElementGeometry(spatialElement)
                               .GetGeometry();
                }
                catch (Exception e)
                {
                    var boundaries = spatialElement.GetBoundarySegments(new SpatialElementBoundaryOptions());
                    MessageBox.Show(boundaries.Count.ToString());

                    foreach (var boundarySegments in boundaries)
                    {
                        foreach (var boundarySegment in boundarySegments)
                        {
                            var curve = boundarySegment.GetCurve() as Line;
                            if (curve == null)
                            {
                                MessageBox.Show("curve is null");
                            }
                            doc.NewLine(curve);
                        }
                    }
                    MessageBox.Show("wrong Message Skip this loop");
                    continue;
                }

                //geometrys.Add(geometry);
                var geometrys1 = new List <GeometryObject>()
                {
                    geometry
                };

                doc.Invoke(m =>
                {
                    var directShape = DirectShape.CreateElement(doc, new ElementId(BuiltInCategory.OST_GenericModel));
                    directShape.AppendShape(geometrys1);
                }, "创建内建模型");
            }

            //SpatialElementGeometryCalculator spatialGeometryCal = new SpatialElementGeometryCalculator(doc);
            //foreach (Room room in rooms)
            //{
            //    var roomGeo = spatialGeometryCal.CalculateSpatialElementGeometry(room);
            //}

            return(Result.Succeeded);
        }
示例#23
0
文件: Command.cs 项目: AMEE/revit
        /// <summary>
        /// Test whether each room has a roof to bound it.
        /// </summary>
        /// <param name="message">Error message to be dumped.</param>
        /// <param name="elements">Some elements to return.</param>
        /// <returns></returns>
        private bool FindRoomBoundingRoofs(ref string message, Autodesk.Revit.DB.ElementSet elements)
        {
            // Get all rooms
            List<Element> rooms = GetRoomsElements();
            if (rooms.Count == 0)
            {
                message = "Unable to identify any rooms, please create room first!";
                return false;
            }

            // Represents the criteria for boundary elements to be considered bounding roofs
            LogicalOrFilter categoryFilter = new LogicalOrFilter(new ElementCategoryFilter(BuiltInCategory.OST_Roofs),
                                                                    new ElementCategoryFilter(BuiltInCategory.OST_RoofSoffit));

            // Calculator for room/space geometry.
            SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(m_document);

            // Stores the resulting room->roof relationships
            Dictionary<Element, List<ElementId>> roomsAndRoofs = new Dictionary<Element, List<ElementId>>();

            foreach (Element room in rooms)
            {
                // Get room geometry & boundaries
                SpatialElementGeometryResults results = calculator.CalculateSpatialElementGeometry((SpatialElement)room);

                // Get solid geometry so we can examine each face
                Solid geometry = results.GetGeometry();

                foreach (Face face in geometry.Faces)
                {
                    // Get list of roof boundary subfaces for a given face
                    IList<SpatialElementBoundarySubface> boundaryFaces = results.GetBoundaryFaceInfo(face);
                    foreach (SpatialElementBoundarySubface boundaryFace in boundaryFaces)
                    {
                        // Get boundary element
                        LinkElementId boundaryElementId = boundaryFace.SpatialBoundaryElement;

                        // Only considering local file room bounding elements
                        ElementId localElementId = boundaryElementId.HostElementId;

                        // Evaluate if element meets criteria using PassesFilter()
                        if (localElementId != ElementId.InvalidElementId && categoryFilter.PassesFilter(m_document, localElementId))
                        {
                            // Room already has roofs, add more
                            if (roomsAndRoofs.ContainsKey(room))
                            {
                                List<ElementId> roofs = roomsAndRoofs[room];
                                if (!roofs.Contains(localElementId))
                                    roofs.Add(localElementId);
                            }
                            // Room found first roof
                            else
                            {
                                List<ElementId> roofs = new List<ElementId>();
                                roofs.Add(localElementId);
                                roomsAndRoofs.Add(room, roofs);
                            }
                            break;
                        }
                    }
                }
            }

            // Format results
            if (roomsAndRoofs.Count > 0)
            {
                String logs = String.Format("Rooms that have a bounding roof:");
                message += logs + "\t\r\n";
                Trace.WriteLine(logs);
                foreach (KeyValuePair<Element, List<ElementId>> kvp in roomsAndRoofs)
                {
                    // remove this room from all rooms list
                    rooms.Remove(kvp.Key);

                    List<ElementId> roofs = kvp.Value;
                    String roofsString;

                    // Single roof boundary
                    if (roofs.Count == 1)
                    {
                        Element roof = m_document.get_Element(roofs[0]);
                        roofsString = String.Format("Roof: Id = {0}, Name = {1}", roof.Id.IntegerValue, roof.Name);
                    }
                    // Multiple roofs
                    else
                    {
                        roofsString = "Roofs ids = " + string.Join(", ", Array.ConvertAll<ElementId, string>(roofs.ToArray(), i => i.ToString()));
                    }

                    // Save results
                    logs = String.Format(
                        "  Room: Id = {0}, Name = {1} --> {2}",
                        kvp.Key.Id.IntegerValue, kvp.Key.Name, roofsString);
                    message += logs + "\t\r\n";
                    Trace.WriteLine(logs);
                }
            }

            // Format the rooms that have no bounding roof
            Trace.WriteLine("Geometry relationship checking finished...");
            if (rooms.Count != 0)
            {
                String logs = String.Format("Below rooms don't have bounding roofs:");
                message += logs + "\t\r\n";
                Trace.WriteLine(logs);
                foreach (Element room in rooms)
                {
                    elements.Insert(room);
                    logs = String.Format("  Room Id: {0}, Room Name: {1}",
                        room.Id.IntegerValue, room.Name);
                    message += logs + "\t\r\n";
                    Trace.WriteLine(logs);
                }
            }

            return true;
        }
示例#24
0
        private void CreateDucts(int jndex)
        {
            if (sortedlocalsTech.ElementAt(jndex).ElementAt(0).Name.Contains("GT24"))
            {
                Debug.WriteLine("TEST GAINE 24");
            }
            Debug.WriteLine(jndex);
            ElementId levelId = ElementId.InvalidElementId;

            tiltingSpaces.Clear();
            GetBestPath();
            GetTiltingSpace();
            GetBestPosition();
            currentConn = null;

            for (int i = 0; i < sortedlocalsTech.ElementAt(jndex).Count();)
            {
                if (sortedlocalsTech.ElementAt(jndex).Count() == 1)
                {
                    Debug.WriteLine("i: " + i);
                    break;
                }

                Element e     = doc.GetElement(sortedlocalsTech.ElementAt(jndex).ElementAt(i).Id);
                var     space = doc.GetElement(sortedlocalsTech.ElementAt(jndex).ElementAt(i).Id) as Space;

                try
                {
                    if (i >= RevitDataContext.lazyInstance.SpacesInfo.Count())
                    {
                        break;
                    }
                    SpatialElementGeometryCalculator calculator = new SpatialElementGeometryCalculator(doc);
                    SpatialElementGeometryResults    results    = calculator.CalculateSpatialElementGeometry(space); // compute the room geometry
                    Solid       roomSolid = results.GetGeometry();
                    List <Face> lf        = new List <Face>();
                    List <XYZ>  Edges     = new List <XYZ>();
                    List <XYZ>  temp      = new List <XYZ>();
                    foreach (Face face in roomSolid.Faces)
                    {
                        foreach (EdgeArray item in face.EdgeLoops)
                        {
                            List <XYZ> lc = JtBoundingBoxXyzExtensionMethods.GetPolygon(item);
                            foreach (var subitem in lc)
                            {
                                temp.Add(subitem);
                            }
                        }
                    }
                    XYZ tempXYZ = null;
                    #region delete identical points, Distinct() linq not that smart
                    foreach (var item in temp)
                    {
                        if (tempXYZ == null)
                        {
                            tempXYZ = item;
                            Edges.Add(item);
                        }
                        else
                        {
                            bool isPresent = false;
                            foreach (var item2 in Edges)
                            {
                                if (item.X == item2.X &&
                                    item.Y == item2.Y &&
                                    item.Z == item2.Z)
                                {
                                    isPresent = true;
                                }
                            }
                            if (isPresent == false)
                            {
                                Edges.Add(item);
                            }
                        }
                    }
                    #endregion

                    Level currentLevel = null;
                    //Get the duct Type
                    FilteredElementCollector collector1 = new FilteredElementCollector(doc);
                    collector1.OfClass(typeof(DuctType));
                    DuctType ductType = null;
                    foreach (Element elem in collector1)
                    {
                        /**
                         * Raccord avec té et coude droit
                         *  Raccord par té avec coude segmenté
                         *  Raccord par piquage et coude segmenté
                         *  Raccord par té et coude droit
                         *  Raccord par piquage et coude droit
                         *  Raccord avec té et coude segmenté
                         *  Raccord par piquage et coude à rayon
                         *  Raccord par piquage et coude segmenté
                         *  Raccord par piquage et coude droit
                         *  Raccord par piquage et coude lisse
                         *  Raccord avec té et coude lisse
                         *  Synoptique de désenfumage
                         *  Raccord par piquage et coude droit chanfreiné
                         *  Raccord avec té et coude à rayon
                         **/
                        if (elem.Name == "Raccord avec té et coude lisse" ||
                            elem.Name == "Connection with tee and smooth elbow")    // gerer english
                        {
                            ductType = elem as DuctType;
                        }
                    }
                    FilteredElementCollector collector2 = new FilteredElementCollector(doc);
                    collector2.OfClass(typeof(MechanicalSystemType)).OfCategory(BuiltInCategory.OST_DuctSystem);
                    MechanicalSystemType mechType = null;
                    foreach (Element e1 in collector2)
                    {
                        /**
                         *  Désenfumage air neuf
                         *  Conduit de Fumée
                         *  Soufflage
                         *  Reprise
                         *  Extraction
                         *  VMC
                         *  Desenfumage Extraction
                         *  Air Neuf
                         *  Rejet
                         *  Desenfumage Air Neuf
                         *  Soufflage Recylage
                         *  Reprise Recyclage
                         *  Soufflage VC
                         *  Soufflage CTA
                         *  ..
                         **/
                        if (e1.Name == "VMC" || e1.Name == "CMV")  // gerer english
                        {
                            mechType = e1 as MechanicalSystemType;
                        }
                    }

                    /**
                     *  Get next space
                     **/


                    bool GetMe = false;
                    int  at    = 0;
                    foreach (var key in RevitDataContext.lazyInstance.SpacesInfo.Keys)
                    {
                        if (key.Number == space.Number)
                        {
                            GetMe = true;
                        }
                        if (GetMe == true)
                        {
                            if (at != 0)
                            {
                                at -= 1;
                            }
                            break;
                        }
                        at += 1;
                    }

                    currentLevel = e.Document.GetElement(e.LevelId) as Level;
                    XYZ startingPoint = null;
                    XYZ endingPoint   = null;

                    /**
                     *  Get the starting point shifted depending on next space location
                     * */

                    Utils.lazyInstance.GetLowestAndHighestPolygon(RevitDataContext.lazyInstance.SpacesInfo.ElementAt(i).Value.Item2, space.Level);
                    List <XYZ> test1 = new List <XYZ>();
                    List <XYZ> test2 = new List <XYZ>();
                    test1 = Utils.lazyInstance.lowestPolyg;
                    test2 = Utils.lazyInstance.highestPolyg;
                    if (test1.Count() != 0 && test2.Count() != 0)
                    {
                        startingPoint = Utils.lazyInstance.GetCenterOfPolygon(test1);
                        endingPoint   = Utils.lazyInstance.GetCenterOfPolygon(test2);
                    }

                    Utils.lazyInstance.GetLowestAndHighestPolygon(RevitDataContext.lazyInstance.SpacesInfo.ElementAt(correspSmallestSpaces[i]).Value.Item2,
                                                                  RevitDataContext.lazyInstance.SpacesInfo.ElementAt(correspSmallestSpaces[i]).Key.Level);
                    List <XYZ> test5 = new List <XYZ>();
                    List <XYZ> test6 = new List <XYZ>();
                    test5 = Utils.lazyInstance.lowestPolyg;
                    test6 = Utils.lazyInstance.highestPolyg;
                    XYZ SendingPoint = Utils.lazyInstance.GetCenterOfPolygon(test6);
                    startingPoint = Utils.lazyInstance.GetCenterOfPolygon(test5);
                    Duct      duct      = null;
                    Connector ductStart = null;
                    Connector ductEnd   = null;
                    Utils.lazyInstance.GetLowestAndHighestPolygon(RevitDataContext.lazyInstance.SpacesInfo.ElementAt(i).Value.Item2,
                                                                  RevitDataContext.lazyInstance.SpacesInfo.ElementAt(i).Key.Level);
                    List <XYZ> test3 = new List <XYZ>();
                    List <XYZ> test4 = new List <XYZ>();
                    test3       = Utils.lazyInstance.lowestPolyg;
                    test4       = Utils.lazyInstance.highestPolyg;
                    endingPoint = new XYZ(SendingPoint.X, SendingPoint.Y, Utils.lazyInstance.GetCenterOfPolygon(test4).Z);

                    if (tiltingSpaces.Contains(correspSmallestSpaces[i]) && i != RevitDataContext.lazyInstance.SpacesInfo.Count() - 1)
                    {
                        XYZ nSt = new XYZ(startingPoint.X - 0.1, startingPoint.Y, startingPoint.Z - 0.8);
                        startingPoint = nSt;
                    }
                    Debug.WriteLine("i: " + i);
                    if (!tiltingSpaces.Contains(i) || i == 0 || i == tiltingSpaces.LastOrDefault())
                    {
                        if (currentConn != null)
                        {
                            XYZ nStart1 = currentConnOrigin;
                            endingPoint = nStart1;
                        }
                        using (Transaction tr = new Transaction(doc))
                        {
                            tr.Start("Create New Duct");
                            {
                                if (currentConn == null)
                                {
                                    duct = Duct.Create(doc, mechType.Id, ductType.Id, RevitDataContext.lazyInstance.SpacesInfo.ElementAt(i).Key.LevelId, startingPoint, endingPoint);
                                }
                                else
                                {
                                    duct = Duct.Create(doc, ductType.Id, RevitDataContext.lazyInstance.SpacesInfo.ElementAt(i).Key.LevelId, currentConn, startingPoint);
                                    Debug.WriteLine("currentConn.Origin: " + currentConn.Origin);
                                    Debug.WriteLine("startingPoint Origin: " + startingPoint);
                                }


                                Parameter parameter = duct.get_Parameter(BuiltInParameter.RBS_CURVE_DIAMETER_PARAM);
                                parameter.Set(diameter);
                                List <Connector> lC = new List <Connector>();
                                foreach (Connector conn in duct.ConnectorManager.Connectors)
                                {
                                    if (conn.ConnectorType == ConnectorType.End)
                                    {
                                        lC.Add(conn);
                                    }
                                }

                                if (lC.ElementAt(0).Origin.Z > lC.ElementAt(1).Origin.Z)
                                {
                                    ductStart = lC.ElementAt(1);
                                    ductEnd   = lC.ElementAt(0);
                                }
                                else
                                {
                                    ductStart = lC.ElementAt(0);
                                    ductEnd   = lC.ElementAt(1);
                                }
                                if (currentConn == null)
                                {
                                    currentConnectors.Add("start" + i, ductStart);
                                    currentConnectors.Add("end" + i, ductEnd);
                                }
                                else
                                {
                                    currentConnectors.Add("start" + i, currentConn);
                                    currentConnectors.Add("end" + i, ductEnd);
                                    doc.Create.NewElbowFitting(ductStart, currentConn);
                                }
                                Debug.WriteLine("Passed, ductStart.Origin : " + ductStart.Origin);
                                tr.Commit();
                                currentConn = ductEnd;
                            }
                        }
                    }

                    // is getting tilted
                    if (tiltingSpaces.Contains(correspSmallestSpaces[i]) &&
                        i != RevitDataContext.lazyInstance.SpacesInfo.Count() - 1 &&
                        correspSmallestSpaces[i] != RevitDataContext.lazyInstance.SpacesInfo.Count() - 1)
                    {
                        Utils.lazyInstance.GetLowestAndHighestPolygon(RevitDataContext.lazyInstance.SpacesInfo.ElementAt(correspSmallestSpaces[i + 1]).Value.Item2,
                                                                      RevitDataContext.lazyInstance.SpacesInfo.ElementAt(correspSmallestSpaces[i + 1]).Key.Level);
                        List <XYZ> test7 = new List <XYZ>();
                        test7 = Utils.lazyInstance.lowestPolyg;
                        var tempZ = startingPoint.Z;
                        endingPoint = new XYZ(Utils.lazyInstance.GetCenterOfPolygon(test7).X, Utils.lazyInstance.GetCenterOfPolygon(test7).Y, tempZ);

                        if (currentConn != null)
                        {
                            Utils.lazyInstance.GetLowestAndHighestPolygon(RevitDataContext.lazyInstance.SpacesInfo.ElementAt(correspSmallestSpaces[correspSmallestSpaces[i] + 1]).Value.Item2,
                                                                          RevitDataContext.lazyInstance.SpacesInfo.ElementAt(correspSmallestSpaces[i + 1]).Key.Level);
                            List <XYZ> test77 = new List <XYZ>();
                            test77 = Utils.lazyInstance.lowestPolyg;
                            var tempZZ = startingPoint.Z;
                            endingPoint = new XYZ(Utils.lazyInstance.GetCenterOfPolygon(test77).X, Utils.lazyInstance.GetCenterOfPolygon(test77).Y, tempZ);
                        }

                        using (Transaction tr2 = new Transaction(doc))
                        {
                            tr2.Start("Create New Tilting Duct");
                            {
                                duct = Duct.Create(doc, mechType.Id, ductType.Id, RevitDataContext.lazyInstance.SpacesInfo.ElementAt(i).Key.LevelId, startingPoint, endingPoint);
                                Debug.WriteLine("startingPoint Origin: " + startingPoint);
                                Debug.WriteLine("endingPoint.Origin: " + endingPoint);

                                Parameter parameter = duct.get_Parameter(BuiltInParameter.RBS_CURVE_DIAMETER_PARAM);
                                parameter.Set(diameter);
                                List <Connector> lC = new List <Connector>();
                                foreach (Connector conn in duct.ConnectorManager.Connectors)
                                {
                                    if (conn.ConnectorType == ConnectorType.End)
                                    {
                                        lC.Add(conn);
                                    }
                                }
                                int tempi = i + 1;
                                if (i != 0)
                                {
                                    tempi = correspSmallestSpaces[correspSmallestSpaces[i] + 1];
                                }
                                // getting the right start and end duct
                                Utils.lazyInstance.GetLowestAndHighestPolygon(RevitDataContext.lazyInstance.SpacesInfo.ElementAt(tempi).Value.Item2,
                                                                              RevitDataContext.lazyInstance.SpacesInfo.ElementAt(tempi).Key.Level);

                                List <XYZ> test8 = new List <XYZ>();
                                test8     = Utils.lazyInstance.lowestPolyg;
                                lC        = Utils.lazyInstance.GetClosestConnector(lC, Utils.lazyInstance.GetCenterOfPolygon(test8));
                                ductStart = lC.ElementAt(0);
                                ductEnd   = lC.ElementAt(1);

                                currentConnOrigin = ductStart.Origin;
                                test11            = ductEnd.Origin;
                                Debug.WriteLine("Start of tilting is :" + ductStart.Origin);
                                Debug.WriteLine("end of tilting is :" + ductEnd.Origin);
                                currentConn = ductStart;
                                doc.Create.NewElbowFitting(ductEnd, currentConnectors.ElementAt(currentConnectors.Count() - 1).Value);
                                currentConnectors.Add("startTilted" + i, ductStart);
                                currentConnectors.Add("endTilted" + i, ductEnd);
                            }
                            tr2.Commit();
                        }
                    }
                    i = correspSmallestSpaces[i] + 1;
                    currentElement = e;
                }
                catch (Exception ex)
                {
                    break;
                }
            }
        }