Chào mừng các bác đã ghé thăm blog của mình.😄
Mục đích sử dụng
Đôi khi việc sao chép hoặc dán đối tượng trong mô hình làm ảnh hưởng đến công việc này, vấn đề có thể xảy ra rất nhiều với trường hợp sao chép nhầm mà khó có thể nhận ra được đối tượng nào trùng lặp, với ví dụ nhỏ dưới này sẽ giúp các bác kiểm tra nhanh những ống nào nằm trong mô hình MEP bị trùng lặp nhé.
Bắt đầu
Đầu tiên mình sẽ lấy về các ống Pipe có trên mô hình và các đường CurveEndpoints để lấy MidPoint lọc ra một mớ list tọa độ của các ống.Giờ thì công việc tiếp theo của mình chính là tìm ra điểm nào trùng mà thôi.
Thuật toán lọc ra đối tượng trùng lặp
mylist = IN[0] | |
i, seen, result = mylist, set(), [] | |
for _index, item in enumerate(i): | |
if item not in seen: | |
seen.add(item) | |
else: | |
result.append(_index) | |
OUT = result |
Giờ thêm tí muối vào để xuất Excel nữa
Và cuối cùng là xóa đối tượng với package Orichid
Kết quả
Video Demo :
Mở rộng
Ngoài cách làm bên trên, bạn cũng có thể sử dụng công cụ BIM interoperability kiểm tra từ Autodesk.Với nút chọn model checker trên thanh công cụ cũng cho phép bạn kiểm tra điều này.
Bây giờ bạn có thể dễ dàng nhìn thấy nhiều đối tượng bị trùng lấp và việc của bạn chỉ cần xuất ra Excel để kiểm tra mà thôi.
Sau khi đưa ra excel thì kết quả bao gồm id đối tượng sẽ trông như thế này.
Bây giờ chúng ta thử quay lại để kiểm tra một Id xem liệu chúng có phải bị Duplicate không.Và kết quả hiện thị cho biết đối tượng đang trùng lặp và cần xử lý chúng.
Cùng với việc mở rộng lên một công cụ ổn định, bạn cũng có thể kiểm tra thông qua boundingbox đối tượng thay vì vị trí đối tượng.
public static bool IsDuplicate(this Element element, Document Doc = null) | |
{ | |
Document doc = Doc ?? element.Document; | |
View view = doc.GetElement(element.OwnerViewId) as View; | |
BoundingBoxXYZ bb; | |
if (view != null) bb = element.get_BoundingBox(view); | |
else bb = element.get_BoundingBox(null); | |
if (bb == null) return false; | |
Outline outline = new Outline(bb.Min, bb.Max); | |
BoundingBoxIntersectsFilter bbfilter | |
= new BoundingBoxIntersectsFilter(outline); | |
FilteredElementCollector collector | |
= new FilteredElementCollector( | |
doc, doc.ActiveView.Id); | |
ICollection<ElementId> idsExclude | |
= new List<ElementId>(); | |
idsExclude.Add(element.Id); | |
List<Element> sameElement = collector | |
.Excluding(idsExclude).WherePasses(bbfilter).WhereElementIsNotElementType().ToElements().ToList(); | |
if (sameElement.Count > 0) | |
{ | |
foreach (Element element1 in sameElement) | |
{ | |
if (element1 is CurveElement) continue; | |
if (element.IsSameLength(element1)) return true; | |
//Not check Detail Line, Curve ARC | |
XYZ lc1 = element1.LocationCenter(); | |
XYZ lc2 = element.LocationCenter(); | |
if (lc1 == null || lc2 == null) continue; | |
bool flag1 = lc1.IsAlmostEqualTo(lc2); | |
bool flag2 = element1.GetType().Name == element.GetType().Name; | |
if (flag1 && flag2) | |
{ | |
return true; | |
} | |
} | |
} | |
return false; | |
} |
Tổng kết
Ở bài này mình chỉ hướng dẫn các bác làm với các loại như ống có CurveEndPoint, vậy với các Famiy không có CurveEndPoint thì sao, gợi ý cho các bác là dùng FamilyInstance.Location
nhé, cuối cùng mình gửi các bác Script cho bác nào còn chưa làm được.Chúc các bác thành công.
Picture : Download
Scripts Dyn : Download
Vậy là mình đã kể cho các bác nghe xong hết câu chuyện nữa rồi đó, cứ thấy gì đó vui vui hay hay là mình lại viết lên cho a e tham khảo và góp ý, nếu có ý tưởng gì giúp cải thiện nhanh hơn thì các bác bình luận bên dưới nhé, mình sẽ bổ sung để bài viết được hoàn thiện hơn.Cám ơn các bác đã ghé thăm blog của mình !