Manual selection or working with preselected elements in a linked model

Hi all,

I’m trying to create a graph where I would like to manually tab-select elements, or get pre-selected elements graph to the script being run. From what I can tell (having queried Chat GPT) I cannot do this in a vanilla dynamo install, so if there is a package with a specific node that can assist, I’d be grateful to hear any recommendations.

I am using Revit 2023.1 with Dynamo 2.16.4.

Thanks

Hi @Barry.Lothian , welcome to the forum.

The Spring package has some useful nodes for selecting elements, either from the current model or a linked model.

Tell chat GPT it has told a lie and must now say 10,000 hail mary’s and 5000 our fathers to atone for it’s sins.

I believe this node has been included with Dynamo for Revit by way of Generative Design since 2021 or 2022 product line, but it is certainly in 2023.

Ordered Selection

:joy:

Hi Jacob,

I’ve just tried your recommendation but it doesn’t work for me. I’m trying to tab-select elements within a linked model. I appear to be able to select elements within the opened file, but when I try tab-selecting, I just hear an error noise.

Hi @Barry.Lothian dont think tap select will work as you think in a linked file, can we do that in revit itself ? you can pick linked elements…i guess…many have done that…i like the way with Genius loci

Hi @sovitek

Yes, I can tab-select linked elements in Revit no problem. If I want to select more than one element, I tab-select the next element then press Ctrl+Left-Click to confirm selection, and rinse & repeat etc…

arhhh sorry, didnt read it right…yeah great :wink:

Ah - missed the link bit.

Assuming you can select one element from the link, are you sure you’ll be able to work with the object? Many functions of the element won’t process linked elements correctly back in 2023.

i just mean as here and probably totally wrong :wink: :wink:

Revit_N8z5YD94NG

The linked elements are pipes, ducts and cable tray families. What I am intending on doing is using a python node to get the size (width & height, or diameter) and material from the selected families, and then insert specific detail families at the location of these families. The Python node will also set parameter values in the detail families, dependant on type of service, and the nature of the value of the material.

The reason for the need for creating this graph is you cannot draw detail lines from the edges of these family types, only their centrepoint.

I’m hoping that Chat GPT hasn’t been hallucinating and giving me incorrect results with the viability of this as a potential solution. The hardest part of the process appears to be selecting the elements in the first instance, which is why I’m wondering if a downloadable package contains a node that will allow me to select elements, or retrieve elements that are already selected

So if you’re reading geometry (location counts), detail items might require converting to the view’s coordinate system for placement. And as you’re working with link elements you might have to convert to the active model’s coordinate system as well… all in you’ve got a fairly significant lift for the benefit of adding non-parametric, non-intelligent data over a 2d view. If you can move past that part of the process I’d recommend doing so.

The detail families themselves are entirely parametric and are ultimately designed to be a huge timesaver due to the inability to snap to the perimeter of these system families.

The current manual workaround is

  1. manually tab-select a pipe or cable tray
  2. scroll and view its size(s) in the relevant instance parameter(s)
  3. activate detail line and offset by 1/2 of the size and draw a horizontal line from the only available snapping point (the centre)
  4. repeat for the vertical

When you have many of these to repeat in multiple elevation views, it becomes a huge PITA, which is why automating the insertion of the detail components (and setting the parameter values all of the different detail lines within them) will hopefully give me a snappable object that will allow me to draw a rectangular opening around the services, which in turn will enable me to adjust the Width, Height and Level above Storey instance parameters for existing Face-based Generic Model void families.

I’m sure the above will sound either quite confusing or convoluted, but this is my current reality and I’m keen to automate as much of this as possible to eliminate repetitive manual operations.

That looks just exactly what I am after. I did try installing the latest version of the package but I didn’t get the pop-up message visible in your screen recording, when I pressed run. It wasn’t abundantly clear which version of the package I should use (a column adjacent to each release with the appropriate Revit version to be used would eliminate any doubt) but I’m guessing that if I’m using Revit 2023 that I should use the most recent version prefixed with 2023.

just use the latest should work, and you remember hit finish in revit ribbon after select ?

If I understand your process correctly, you’re automating a detail item so that you have references to manually create another element with those same bounds. Why not just skip the detail item and automate the creation of the void family with the correct opening size? I think you can automate (and simplify) a lot of your current process still.

I replicated your node setup and pressed run but nothing happened. I can only conclude it was something to do with the version of the package I was using.

The void families are already present in the model and are created by an Add-in. My task is to update these to suit updated service positions by determining where the perimeter of the opening should be and checking specific clearances that each service has relative to others (whether they be identical or different). A lot of it has to do with combustibility and compliance with fire-stopping manufacturers documentation. The Detail Items (when placed) will allow me to see if any services are too close to each other as well as aiding creation of the temporary linework for the opening.

That still feels like something that could be fully automated around the void families unless there’s a ton of design intuition that goes into making those decisions. If it’s just updating the position and/or clearances based on opening size, then it should be a straightforward automation of the objects and their properties. If the complicated part is what happens after you’ve identified a collision, then you could automate everything to that point and then flag the problematic areas. Just food for thought.

hi,

here is an example

import clr
import sys
import System
#import net library
from System import Array
from System.Collections.Generic import List, IList, Dictionary, HashSet

#import Revit API
clr.AddReference('RevitAPI')
import Autodesk
from Autodesk.Revit.DB import *
import Autodesk.Revit.DB as DB

#import Revit APIUI namespace
clr.AddReference('RevitAPIUI')
import Autodesk.Revit.UI as RUI
from Autodesk.Revit.UI.Selection import *

#import transactionManager and DocumentManager (RevitServices is specific to Dynamo)
clr.AddReference('RevitServices')
import RevitServices
from RevitServices.Persistence import DocumentManager
from RevitServices.Transactions import TransactionManager
doc = DocumentManager.Instance.CurrentDBDocument
uiapp = DocumentManager.Instance.CurrentUIApplication
uidoc = uiapp.ActiveUIDocument
app = uiapp.Application

    
def get_AllLinkElementConnected():
    #subfunction
    def getSubConnect(elem):
        lstElems = [elem]
        lstIds = [elem.Id]
        n = 0
        while n < 2000: # max iteration to search
            n += 1
            init_len = len(lstElems)
            #
            for cdcCheck in lstElems:
                if hasattr(cdcCheck, 'ConnectorManager'):
                    conManag = cdcCheck.ConnectorManager
                else:
                    conManag = cdcCheck.MEPModel.ConnectorManager            
                for con in conManag.Connectors :
                    for conRef in con.AllRefs:
                        if conRef.Owner.Id not in lstIds:
                            #list ConnectorType must to be adapted
                            if conRef.ConnectorType in [ConnectorType.End, ConnectorType.Surface, ConnectorType.Curve]:
                                lstElems.append(conRef.Owner)
                                lstIds.append(conRef.Owner.Id)
            #
            # if no elements added break the while loop
            if len(lstElems) == init_len:
                break
                            
            return lstElems
    #
    ### main function ###
    ref = uidoc.Selection.PickObject(ObjectType.LinkedElement, "Select Link Element")
    lnk_instance = doc.GetElement(ref)
    lnk_doc = lnk_instance.GetLinkDocument()
    lnk_elem = lnk_doc.GetElement(ref.LinkedElementId )
    
    subElemsConnected = getSubConnect(lnk_elem)
    subElemsConnected_refs = List[Reference]([Reference(x).CreateLinkReference(lnk_instance) for x in subElemsConnected])
    uidoc.Selection.SetReferences(subElemsConnected_refs)
    return subElemsConnected
    
OUT = get_AllLinkElementConnected()