using Autodesk.Revit.ApplicationServices; using Autodesk.Revit.DB; using Autodesk.Revit.DB.Events; using Autodesk.Revit.DB.Plumbing; using Autodesk.Revit.UI; using Autodesk.Revit.UI.Events; using DevExpress.Utils.Extensions; using HStation.RevitDev.Model.ModelEnum; using HStation.RevitDev.RevitDataExport.Common; using HStation.RevitDev.RevitDataExport.Entity; using HStation.RevitDev.RevitDataExport.Service; using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Linq; using static DevExpress.Data.Mask.Internal.RegExMaskMath.CloudOfInts; namespace HStation.RevitDev.RevitDataExport.Utility { public static class DocumentUtil { public static void RegistDocumentEvent(ExternalCommandData commandData) { commandData.Application.Application.DocumentChanged -= App_DocumentChanged; commandData.Application.Application.DocumentChanged += App_DocumentChanged; GlobalResource.CurrentUIDocument = commandData.Application.ActiveUIDocument; RegistViewEvent(commandData); } private static void App_DocumentChanged(object sender, DocumentChangedEventArgs e) { var doc = e.GetDocument(); try { var addedIds = e.GetAddedElementIds(); var removeIds = e.GetDeletedElementIds(); var modifiedIds = e.GetModifiedElementIds(); AddElements(doc, addedIds); RemoveElements(removeIds); ModifyElements(modifiedIds); UpdateLinkerInfo(doc); GlobalResource.InstancePanel.UpdateForm(); } catch (Exception ex) { TaskDialog.Show("错误", ex.Message); } } private static void UpdateLinkerInfo(Document doc) { foreach (var pair in GlobalResource.RevitModels) { foreach (var model in pair.Value) { var id = model.Id; var element = doc.GetElement(new ElementId(int.Parse(id))); var linkedElems = element.GetConnectElements(); var linkedIds = linkedElems.Select(x => x.Id.IntegerValue.ToString()); model.LinkIds = string.Join(",", linkedIds); } } } private static void ModifyElements(ICollection modifiedIds) { foreach (var id in modifiedIds) { if (GlobalResource.ElementIds.Contains(id.IntegerValue.ToString())) { } } } private static void RemoveElements(ICollection removeIds) { foreach (var id in removeIds) { var strId = id.IntegerValue.ToString(); if (GlobalResource.ElementIds.Contains(strId)) { GlobalResource.ElementIds.Remove(id.IntegerValue.ToString()); foreach (var pair in GlobalResource.RevitModels) { var values = pair.Value; var model = values.Where(x => x.Id == strId)?.ToList(); if (model == null || model.Count() == 0) { continue; } else { values.Remove(model[0]); } } } } return; } private static void AddElements(Document doc, ICollection addedIds) { bool instancePlacing = GlobalResource.InstancePlacing; bool pipePlacing = GlobalResource.PipePlacing; if (pipePlacing) { foreach (var id in addedIds) { var elem = doc.GetElement(id); if (elem is FamilyInstance fi) { AddAutoCreated(fi); } if (elem is Pipe) { GlobalResource.ElementIds.Add(id.IntegerValue.ToString()); AddManualCreated(elem); } } } else if (instancePlacing) { foreach (var id in addedIds) { var elem = doc.GetElement(id); if (elem is FamilyInstance) { GlobalResource.ElementIds.Add(id.IntegerValue.ToString()); AddManualCreated(elem); } } } else { bool isPumpSystemElement = false; foreach (var id in addedIds) { if (IsConnectedWithPumpSystem(doc, id)) { isPumpSystemElement = true; break; } } if (isPumpSystemElement) { foreach (var id in addedIds) { AddToPumpSystem(doc, id); } } } return; } private static bool IsConnectedWithPumpSystem(Document doc, ElementId id) { var elem = doc.GetElement(id); if (elem is Pipe pipe) //直接点击水泵的连接件创建管道 { if (pipe.ConnectWithPumpSystem()) { //GlobalResource.ElementIds.Add(id.IntegerValue.ToString()); //TaskDialog.Show("提示", "增加管道:" + id.IntegerValue.ToString()); //AddManualCreated(elem); return true; } } else if (elem is FamilyInstance fi) { if (fi.ConnectWithPumpSystem()) //直接点击管道连接点创建管道时,Revit会自动创建弯头,都需要加入到缓存 { //GlobalResource.ElementIds.Add(id.IntegerValue.ToString()); //TaskDialog.Show("提示", "增加族实例:" + id.IntegerValue.ToString()); //AddManualCreated(elem); return true; } } return false; } private static void AddToPumpSystem(Document doc, ElementId id) { var elem = doc.GetElement(id); if (elem is Pipe) { GlobalResource.ElementIds.Add(id.IntegerValue.ToString()); AddToMap(elem, RevitType.RFT_Pipe); } else if (elem is FamilyInstance fi) { GlobalResource.ElementIds.Add(id.IntegerValue.ToString()); AddAutoCreated(fi); } return; } private static void AddAutoCreated(FamilyInstance fi) { var id = fi.Id; GlobalResource.ElementIds.Add(id.IntegerValue.ToString()); if (fi.IsWanTou()) { AddToMap(fi, RevitType.RFT_Elbow); } else if (fi.IsConverter()) { AddToMap(fi, RevitType.RFT_Converter); } else if (fi.IsSanTong()) { AddToMap(fi, RevitType.RFT_ThreeJoint); } else if (fi.IsSiTong()) { AddToMap(fi, RevitType.RFT_FourJoint); } else { TaskDialog.Show("警告", $"未知类型被添加!id:{fi.Id.IntegerValue}"); //报错 } } private static void AddManualCreated(Element elem) { var id = elem.Id.IntegerValue.ToString(); //更新已加入到缓存中的构件数据 List linkedIds = elem.GetConnectElements().Select(x => x.Id.IntegerValue.ToString()).ToList(); //foreach (var linkId in linkedIds) //{ // var model = GlobalResource.GetElementModel(linkId); // if (!model.LinkIds.Contains(id)) // { // model.LinkIds += "," + id; // } //} //把新增构件加入到缓存中 if (!GlobalResource.RevitModels.ContainsKey(GlobalResource.RevitFamilyType)) { GlobalResource.RevitModels.Add(GlobalResource.RevitFamilyType, new ObservableCollection()); GlobalResource.RevitModels[GlobalResource.RevitFamilyType].Add(new ElementModel { Name = elem.Name, Id = id, LinkIds = /*string.Join(",", linkedIds)*/string.Empty }); } else if(!GlobalResource.RevitModels[GlobalResource.RevitFamilyType].Any(x=>x.Id == id)) { GlobalResource.RevitModels[GlobalResource.RevitFamilyType].Add(new ElementModel { Name = elem.Name, Id = id, LinkIds = /* string.Join(",", linkedIds)*/string.Empty }); } } private static void AddToMap(Element elem, RevitType revitType) { var id = elem.Id.IntegerValue.ToString(); //更新已加入到缓存中的构件数据 //List linkedIds = elem.GetConnectElements().Select(x => x.Id.IntegerValue.ToString()).ToList(); //foreach (var linkId in linkedIds) //{ // var model = GlobalResource.GetElementModel(linkId); // if (!model.LinkIds.Contains(id)) // { // model.LinkIds += "," + id; // } //} if (!GlobalResource.RevitModels.ContainsKey(revitType)) { GlobalResource.RevitModels.Add(revitType, new ObservableCollection()); GlobalResource.RevitModels[revitType].Add(new ElementModel { Name = elem.Name, Id = id, LinkIds = /*string.Join(",", linkedIds)*/string.Empty }); } else if (!GlobalResource.RevitModels[revitType].Any(x => x.Id == id)) { GlobalResource.RevitModels[revitType].Add(new ElementModel { Name = elem.Name, Id = id, LinkIds = /*string.Join(",", linkedIds)*/string.Empty }); } } public static void RegistViewEvent(ExternalCommandData commandData) { commandData.Application.ViewActivated -= Application_ViewActivated; commandData.Application.ViewActivated += Application_ViewActivated; } private static void Application_ViewActivated(object sender, ViewActivatedEventArgs e) { GlobalResource.CurrentDocument = e.CurrentActiveView.Document; } public static List GetModelElements(this Document doc) { //FilteredElementCollector collector = null; //foreach (Category cate in doc.Settings.Categories) //{ // if (cate.CategoryType != CategoryType.Model) // { // continue; // } // var subCollector = new FilteredElementCollector(doc); // subCollector.OfCategory((BuiltInCategory)(cate.Id.IntegerValue)); // subCollector.WhereElementIsNotElementType(); // if (collector == null) // { // collector = subCollector; // } // else // { // collector.UnionWith(subCollector); // } //} // var collector1 = new FilteredElementCollector(doc). OfCategory(BuiltInCategory.OST_PipeCurves). WhereElementIsNotElementType(); var collector2 = new FilteredElementCollector(doc). OfClass(typeof(FamilyInstance)). WhereElementIsNotElementType(); var elements1 = collector1.ToElements()?.ToList(); var elements2 = collector2.ToElements()?.ToList(); elements1.AddRange(elements2); elements1 = elements1.Where(x => x.Category.CategoryType == CategoryType.Model).ToList(); elements1 = elements1.Where(x => x.get_BoundingBox(null) != null).ToList(); return elements1; } public static void AddUnhandledElementsToCache() { var elements = GlobalResource.CurrentDocument.GetModelElements(); foreach (var element in elements) { var id = element.Id.IntegerValue.ToString(); if (GlobalResource.ElementIds.Contains(id)) { continue; } RevitMepCategoryService.MatchElement(element); } UpdateLinkerInfo(GlobalResource.CurrentDocument); } } }