Can we extract all elements of subcategory while operating in a project file?

Hello, dynamoers.

About the subject in the topic, I would like someone to tell me whether it is practicable to get all elements of subcategory when you open Dynamo with a project file.

I set several subcategories called for instance “plate01” to “plate10” with a numbering order associated to Generic Model Category.

Once I tried to search the solution in Forum and found this "All Elements of Subcategory" - #5 by Andreas_Dieckmann shows that the package with the same function as I want doesn’t work when you open a project file.

Furthermore, I attempted a code below (created by ms copilot and I modified it a little bit) for getting all elements of subcategory “plate01” but the result was NULL.
Honestly, I still don’t understand the meaning of this code, esp. the last two paragraphs.

Any experiences/thoughts are welcome. Thanks. :slight_smile:

import clr

# Import ToDSType(bool) extension method
clr.AddReference("RevitNodes")
import Revit
clr.ImportExtensions(Revit.Elements)

# Import geometry conversion extension methods
clr.ImportExtensions(Revit.GeometryConversion)

# Import DocumentManager and TransactionManager
clr.AddReference("RevitServices")
import RevitServices
from RevitServices.Persistence import DocumentManager
from RevitServices.Transactions import TransactionManager

# Import RevitAPI
clr.AddReference("RevitAPI")
import Autodesk
from Autodesk.Revit.DB import *
from Autodesk.Revit.DB.Structure import *

doc = DocumentManager.Instance.CurrentDBDocument

# Get all elements of a specific category
elements = FilteredElementCollector(doc).OfCategory(BuiltInCategory.OST_GenericModel).WhereElementIsNotElementType().ToElements()

# Get all elements of a specific subcategory
sub_category_name = "plate01"
sub_category = Category.GetCategory(doc, BuiltInCategory.OST_GenericModel)
sub_elements = FilteredElementCollector(doc).OfCategoryId(sub_category.Id).WhereElementIsNotElementType().ToElements()

# Extract elements of a subcategory
sub_elements_data = []
for element in sub_elements:
    sub_element_data = {}
    sub_element_data["Name"] = element.Name
    sub_element_data["Id"] = element.Id
    sub_element_data["Location"] = element.Location.Point
    sub_elements_data.append(sub_element_data)

# Print the extracted data
for data in sub_elements_data:
    print(data)


With this script and some pre/post processing you can do what you want?
(Family SubCategory is from GeniusLoci.)

You need to use the property .SubCategories of the class Categorie.

Thanks for your suggestion.

Here is the trial of your node (I omitted some of them as I reckon they are not necessary) applied to my data.
Now, I’m able to extract subcategories but not to get all of elements of the nested family (proved in the last node).

At least, I had one step forward. Appreciate it.

Thanks for your comments.
But, I’m so sorry that I am still beginner at structing code so I cannot modify my code on my own.
Could you show me the reflected Python code? (I am still on my way Dynamo Primer.)


Like this?

Thanks, @jw.vanasselt !!! It worked very well.
I could extract category object and its name object.

Then, gaining the certain elements of the subcategories namely, “plate01” to “plate10” is the next step for my plan.
Eventually, I would like to get solid (Dynamo geometry) of the subcategories as an output.

I’m sorry that I didn’t distinguish elements and geometries.

Hi @csys17014 ,

You need to retrieve the Dynamo Elements.
I write alot in C# so I had to switch to python / dynamo :grin:

Over here an example:

# Load the Python Standard and DesignScript Libraries
import sys
import clr
clr.AddReference('ProtoGeometry')
from Autodesk.DesignScript.Geometry import *

clr.AddReference("RevitNodes")
import Revit
clr.ImportExtensions(Revit.Elements)

# Import geometry conversion extension methods
clr.ImportExtensions(Revit.GeometryConversion)

# Import DocumentManager and TransactionManager
clr.AddReference("RevitServices")
import RevitServices
from RevitServices.Persistence import DocumentManager
from RevitServices.Transactions import TransactionManager

# Import RevitAPI
clr.AddReference("RevitAPI")
import Autodesk
from Autodesk.Revit.DB import *
from Autodesk.Revit.DB.Structure import *

# Current Document
doc = DocumentManager.Instance.CurrentDBDocument

# Get the Autodesk Elements
elements = FilteredElementCollector(doc).OfCategory(BuiltInCategory.OST_GenericModel).ToElements()

# Empty list
sorted_elements = []

# Look into all elements
for e in elements:
	# Get for each element the subcategories
	subcategory = e.Category.SubCategories
	# Look into all subcategories
	for subcat in subcategory:
		# Create a variable name with the name of the subcategory
		name = subcat.Name
		#If the name of the subcategorie is the same as IN[0]
		if(name == IN[0]):
			# Add the element in to the empty list and convert to Dynamo Element
			sorted_elements.Add(e.ToDSType(True))

OUT = sorted_elements

If you want to write in python I recommend you learn the basics of python and especially understand the revitapidocs.
Such as, what are members, methods and properties of a specific class.

I hope this helps.

2 Likes

I couldn’t appreciate more.
You not only did suggest and show your example but also put informative comments for each line.

I duly noted your remarks of the tips about learning python.

2 Likes

Glad I could help! :slight_smile: