public static Output <List <List <Room> >, List <oM.Geometry.SettingOut.Level> > MapToLevel(List <Room> rooms, List <oM.Geometry.SettingOut.Level> levels, int decimals = 6) { List <List <Room> > roomsByLevel = new List <List <Room> >(); List <oM.Geometry.SettingOut.Level> levelsInUse = new List <oM.Geometry.SettingOut.Level>(); List <oM.Geometry.SettingOut.Level> roundedLevels = new List <oM.Geometry.SettingOut.Level>(); for (int x = 0; x < levels.Count; x++) { oM.Geometry.SettingOut.Level lvl = new oM.Geometry.SettingOut.Level { Elevation = Math.Round(levels[x].Elevation, decimals), Name = levels[x].Name, Fragments = levels[x].Fragments, CustomData = levels[x].CustomData }; roundedLevels.Add(lvl); //Round the levels } Dictionary <double, List <Room> > mappedRooms = new Dictionary <double, List <Room> >(); //Map everything foreach (Room room in rooms) { BoundingBox bbox = room.Perimeter.IBounds(); double zLevel = Math.Round(bbox.Min.Z, decimals); int levelIndex = roundedLevels.IndexOf(roundedLevels.Where(x => x.Elevation == zLevel).First()); if (levelIndex == -1) { BH.Engine.Reflection.Compute.RecordWarning("Room with ID " + room.BHoM_Guid + " does not sit on any provided level"); continue; //zLevel does not exist in the search levels } if (!mappedRooms.ContainsKey(levels[levelIndex].Elevation)) { mappedRooms.Add(levels[levelIndex].Elevation, new List <Room>()); } levelsInUse.Add(levels[levelIndex]); mappedRooms[levels[levelIndex].Elevation].Add(room); } foreach (KeyValuePair <double, List <Room> > kvp in mappedRooms.OrderBy(x => x.Key)) { roomsByLevel.Add(kvp.Value); } Output <List <List <Room> >, List <oM.Geometry.SettingOut.Level> > output = new Output <List <List <Room> >, List <oM.Geometry.SettingOut.Level> > { Item1 = roomsByLevel, Item2 = levelsInUse.OrderBy(x => x.Elevation).Distinct().ToList(), }; return(output); }
/***************************************************/ /**** Public methods ****/ /***************************************************/ public static Level ToRevitLevel(this oM.Geometry.SettingOut.Level level, Document document, RevitSettings settings = null, Dictionary <Guid, List <int> > refObjects = null) { Level revitLevel = refObjects.GetValue <Level>(document, level.BHoM_Guid); if (revitLevel != null) { return(revitLevel); } settings = settings.DefaultIfNull(); List <Level> existingLevels = new FilteredElementCollector(document).OfClass(typeof(Level)).Cast <Level>().ToList(); if (existingLevels.Any(x => x.Name == level.Name)) { BH.Engine.Reflection.Compute.RecordError($"Level named {level.Name} could not be created because a level with the same name already exists in the model. BHoM_Guid: {level.BHoM_Guid}"); return(null); } double elevation = level.Elevation.FromSI(UnitType.UT_Length); if (existingLevels.Any(x => Math.Abs(x.ProjectElevation - elevation) < settings.DistanceTolerance)) { BH.Engine.Reflection.Compute.RecordError($"Level with elevation {level.Elevation} could not be created because a level with the same elevation already exists in the model. BHoM_Guid: {level.BHoM_Guid}"); return(null); } revitLevel = Level.Create(document, elevation); revitLevel.CheckIfNullPush(level); if (revitLevel == null) { return(null); } revitLevel.Name = level.Name; // Copy parameters from BHoM object to Revit element revitLevel.CopyParameters(level, settings); refObjects.AddOrReplace(level, revitLevel); return(revitLevel); }
/***************************************************/ /**** Public Methods ****/ /***************************************************/ public static BH.oM.Geometry.SettingOut.Level LevelFromRevit(this Level revitLevel, RevitSettings settings = null, Dictionary <string, List <IBHoMObject> > refObjects = null) { settings = settings.DefaultIfNull(); oM.Geometry.SettingOut.Level level = refObjects.GetValue <oM.Geometry.SettingOut.Level>(revitLevel.Id); if (level != null) { return(level); } level = BH.Engine.Geometry.Create.Level(revitLevel.ProjectElevation.ToSI(UnitType.UT_Length)); level.Name = revitLevel.Name; //Set identifiers, parameters & custom data level.SetIdentifiers(revitLevel); level.CopyParameters(revitLevel, settings.ParameterSettings); level.SetProperties(revitLevel, settings.ParameterSettings); refObjects.AddOrReplace(revitLevel.Id, level); return(level); }
/***************************************************/ public static Element ToRevit(this oM.Geometry.SettingOut.Level level, Document document, RevitSettings settings = null, Dictionary <Guid, List <int> > refObjects = null) { return(level.ToRevitLevel(document, settings, refObjects)); }
public static Output <List <List <IRegion> >, List <oM.Geometry.SettingOut.Level>, List <IRegion> > MapToLevel(List <IRegion> regions, List <oM.Geometry.SettingOut.Level> levels, int decimals = 6) { List <List <IRegion> > regionsByLevel = new List <List <IRegion> >(); List <oM.Geometry.SettingOut.Level> levelsInUse = new List <oM.Geometry.SettingOut.Level>(); List <IRegion> regionsNotByLevel = new List <IRegion>(); List <oM.Geometry.SettingOut.Level> roundedLevels = new List <oM.Geometry.SettingOut.Level>(); for (int x = 0; x < levels.Count; x++) { oM.Geometry.SettingOut.Level lvl = levels[x].DeepClone(); lvl.Elevation = Math.Round(lvl.Elevation, decimals); roundedLevels.Add(lvl); //Round the levels } Dictionary <double, List <IRegion> > mappedRooms = new Dictionary <double, List <IRegion> >(); //Map everything foreach (IRegion region in regions) { BoundingBox bbox = region.Perimeter.IBounds(); double zLevel = Math.Round(bbox.Min.Z, decimals); oM.Geometry.SettingOut.Level roundedLevel = roundedLevels.Where(x => x.Elevation == zLevel).FirstOrDefault(); if (roundedLevel == null) { regionsNotByLevel.Add(region); continue; //zLevel does not exist in the search levels } int levelIndex = roundedLevels.IndexOf(roundedLevel); if (levelIndex == -1) { regionsNotByLevel.Add(region); continue; //zLevel does not exist in the search levels } if (!mappedRooms.ContainsKey(levels[levelIndex].Elevation)) { mappedRooms.Add(levels[levelIndex].Elevation, new List <IRegion>()); } levelsInUse.Add(levels[levelIndex]); mappedRooms[levels[levelIndex].Elevation].Add(region); } foreach (KeyValuePair <double, List <IRegion> > kvp in mappedRooms.OrderBy(x => x.Key)) { regionsByLevel.Add(kvp.Value); } Output <List <List <IRegion> >, List <oM.Geometry.SettingOut.Level>, List <IRegion> > output = new Output <List <List <IRegion> >, List <oM.Geometry.SettingOut.Level>, List <IRegion> > { Item1 = regionsByLevel, Item2 = levelsInUse.OrderBy(x => x.Elevation).Distinct().ToList(), Item3 = regionsNotByLevel, }; if (regionsNotByLevel.Count > 0) { BH.Engine.Reflection.Compute.RecordWarning("Some regions were not able to be mapped to a level. See the regionsNotMapped output to examine which regions and resolve any issues"); } return(output); }