当前位置:网站首页>Revit secondary development - link file collision detection

Revit secondary development - link file collision detection

2022-07-07 22:22:00 Hey, hey, hey, hey, hey

The function is probably to detect the elements in the project ( Include components in linked files ) Conflict or not

General train of thought :

1、 First get all the converted components in the linked file solid, Transformed solid You can directly detect the elements in the project

2、 Get all edges of the element to be compared 、 Noodles 、solid

3、 If the element has edges : With edges and solid Make a test , If it is not detected, the face and edge need to be detected ;    If the element has no edges : Test with face and face

----------------------------------------------------------------------

Filter linked file internals

//key: Link to the file id   value: Internals id
Dictionary<ElementId,List<ElementId>> m_dicLinkIns;
// Filter linked files 
FilteredElementCollector fecLinks = new FilteredElementCollector(doc);
List<Element> lstElem = fecLinks.ofClass(typeof(RevitLinkInstance)).ToElements().ToList();
// Filter internals 
foreach(Element elem in lstElem)
{
    RevitLinkInstance rvtLinkIns = elem as RevitLinkInstance;
    if(rvtLinkIns == null) continue;
    // Get the linked file document 
    Document linkDoc = rvtLinkIns.GetLinkDocument();
    if(linkDoc == null) continue;
    FilteredElementCollector fecLinkElems = new FilteredElementCollector;
    ElementClassFilter insFilter = new ElementClassFilter (typeof(FamilyInstance));
    ElementClassFilter hostFilter = new ElementClassFilter (typeof(HostObject));
    LogicalOrFilter filter = new LogicalOrFilter (insFilter,hostFilter);
    List<ElementId> lstEids = fecLinkElems.WherePasses(filter).ToElementIds().ToList();
    m_dicLinkIns.Add(rvtLinkIns.id,lstEids);
}

Link the components in the file solid convert , And get the face 、 edge

List<SolidModel> m_lstModels;
private void TransformSolid(Document doc,Element elem)
{
    ElementId linkId = null;
    RevitLinkInstance rvtLinkIns = null;
    if(elem.Document.IsLinked)
    {// If it is a component of a linked document , You need to find the corresponding link file 
        foreach(Elementid eid in m_dicLinkIns.Keys)
        {
            if(m_dicLinkIns[eid].Contains(elem.Id))
            {
                rvtLinkIns = doc.GetElement(eid) as RevitLinkInstance;
                break;
            }
        }
    }
    List<Solid> lstSolids = GetSolids(elem);
    foreach(Solid solid in lstSolids)
    {
        Solid tempSolid = solid;
        if(rvtLinkIns != null)// Generate a converted solid
            tempSolid = SolidUtils.CreateTransformed(solid,rvtLinkIns.GetTransform());
        m_lstModels.lstSolids.Add(tempSolid);
        foreach(Face face in tempSolid.Faces)
        {// Get face 
            m_lstModels.lstFaces.Add(face);
        }
        foreach(Edge edge in tempSolid.Edges)
        {// Get edge 
            Curve curve = edge.AsCurve();
            m_lstModels.lstEdges.Add(curve);
        }
    }
}

If you don't know how to get elements Solid, You can check online , You can also look at another article that I wrote . At the bottom of the link

Collision detection , Two cases

1. Entities have edges , Use entities and edges to measure , If it is not detected, use the face and edge to measure ;

foreach(Curve curve in rightModel.lstEdges)
{
    foreach(Solid solid in leftModel.lstSolids)
    {
        SolidCurveIntersectionoPtions opt = new SolidCurveIntersectionoPtions();
        //solid Check with the edge 
        SolidCurveIntersection result = solid.IntersectWithCurve(curve,opt);
        if(result.SegmentCount > 0)
        {
            // The collision 
        }
        else
        {
            foreach(Face face in solid.Faces)
            {
                IntersectionResultArray array = null;
                //solid Check the face and edge of 
                SetComparisonResult result2 = face.Intersect(curve,out array);
                if(array != null && result2 != SetComparisonResult.Disjoint)
                {
                    // The collision 
                }
            }
        }
    }
}

 

2. Entities have no edges , Test with face to face

foreach(Face rface in rightModel.lstFaces)
{
    foreach(Face lface in leftModel.lstFaces)
    {
        Curve curve = null;
        FaceIntersectionFaceResult result = lface.Intersect(rface, out curve);
        if(result == FaceIntersectionFaceResult.Intersecting)
        {
            // The collision 
        }
    }
}

SolidModel class

public class SolidModel
{
    // Elements id
    public ElementId id {get;set;}
    // Element entities 
    public List<Solid> lstSolids {get;set;}
    // Element edge 
    public List<Curve> lstEdges {get;set;}
    // Element face 
    public List<Face> lstFaces {get;set;}

    public SolidModel()
    {
        lstSolids =new List<Solid>();
        lstEdges =new List<Curve>();
        lstFaces =new List<Face>();
    }
}

-------------------------------------------

Code for a reference , Can't run directly .

原网站

版权声明
本文为[Hey, hey, hey, hey, hey]所创,转载请带上原文链接,感谢
https://yzsam.com/2022/02/202202130606207067.html