Dynamo Python Node - Changing "AND or OR" on Parameter Filter Element

Hi Everyone

First off I understand you are all probably an extremely busy people so if you take the time to read this or help thank you very much!

The python node I’m trying to build is to toggle the “AND or OR” options when building a Parameter Filter Elements as by default when created with Dynamo they are set to “AND”.

As far as I’m aware no OTB nodes or current packages for Dynamo have nodes that can do this inside of them?

But through research I have found that these options are available through the API and I have found some bits of python on this forum but they are building the filter rules inside the python node not getting them as a input.

I’m really quite new to python/coding but I have usually been able to get by with the help of this forum + others and somewhat being able to read and slightly modify bits of python to get the outcome I require, but not this time.

I have tried to 2 methods both without the success I wanted. I think it’s due to me being so ‘green’ and not fully understanding the casting or how to convert one type into another before casting?

Method 1

Create the filter then after it is made change the “AND or OR” with input of Parameter Filter Element (In future another input that would be bool for AND or OR)
-This would cause the least disruption to existing graphs as it’s an additional node after the creation of the filter to toggle “AND or OR”.
ERROR - TypeError: Unable to cast object of type ‘Autodesk.Revit.DB.ParameterFilterElement’ to type ‘Autodesk.Revit.DB.ElementParameterFilter’.

import clr
clr.AddReference('ProtoGeometry')
from Autodesk.DesignScript.Geometry import *

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

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

# Import ToDSType(bool) extension method
clr.AddReference("RevitNodes")
import Revit
clr.ImportExtensions(Revit.Elements)
# Import ToProtoType, ToRevitType geometry conversion extension methods
clr.ImportExtensions(Revit.GeometryConversion)

# Import DSCore nodes in Dynamo
clr.AddReference('DSCoreNodes')
import DSCore
from DSCore import *

# Import python library
import sys
pyt_path = r'C:\Program Files (x86)\IronPython 2.7\Lib'
sys.path.append(pyt_path)
import os
import shutil
import math
# Import math library
from math import *

#Import Data and Time
from datetime import datetime
now = datetime.now()

#Import System Library
import System
from System.Collections.Generic import *
from System.IO import Directory, Path

doc = DocumentManager.Instance.CurrentDBDocument
uiapp = DocumentManager.Instance.CurrentUIApplication
app = uiapp.Application
def ToList(x):
	if isinstance(x,list): return UnwrapElement(x)
	else: return [UnwrapElement(x)]
	
#Preparing input from dynamo to revit
iParafilele = ToList(IN[0])
filterele = List[ElementParameterFilter](iParafilele)
	
Parafilele = []
		
fRule = LogicalOrFilter(filterele)

#Do some action in a Transaction
TransactionManager.Instance.EnsureInTransaction(doc)
paraele.SetElementFilter(fRule)
Parafilele.append(paraele)
TransactionManager.Instance.TransactionTaskDone()

#Final output
OUT = Parafilele

Method 2

Create the filter with python using inputs – Name, Categories, Filter Rules (In future another input that would be bool for AND or OR)
-I like this option as the most robust all in one node solution but will require replacement of nodes in graphs (which isn’t an issue).
ERROR - TypeError: Unable to cast object of type ‘Revit.Filter.FilterRule’ to type ‘Autodesk.Revit.DB.FilterRule’.

import clr
clr.AddReference('ProtoGeometry')
from Autodesk.DesignScript.Geometry import *

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

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

# Import ToDSType(bool) extension method
clr.AddReference("RevitNodes")
import Revit
clr.ImportExtensions(Revit.Elements)
# Import ToProtoType, ToRevitType geometry conversion extension methods
clr.ImportExtensions(Revit.GeometryConversion)

# Import DSCore nodes in Dynamo
clr.AddReference('DSCoreNodes')
import DSCore
from DSCore import *

# Import python library
import sys
pyt_path = r'C:\Program Files (x86)\IronPython 2.7\Lib'
sys.path.append(pyt_path)
import os
import shutil
import math
# Import math library
from math import *

#Import Data and Time
from datetime import datetime
now = datetime.now()

#Import System Library
import System
from System.Collections.Generic import *
from System.IO import Directory, Path

doc = DocumentManager.Instance.CurrentDBDocument
uiapp = DocumentManager.Instance.CurrentUIApplication
app = uiapp.Application
def ToList(x):
	if isinstance(x,list): return UnwrapElement(x)
	else: return [UnwrapElement(x)]
	
#Preparing input from dynamo to revit
names = ToList(IN[0])
cats = ToList(IN[1])
rul = ToList(IN[2])

catids = List[ElementId]()
catids.Clear()
for cc in cats:
	catids.Add(cc.Id)
	

filterrul = List[FilterRule](rul)
	
Parafilele = []
		
fRule = LogicalOrFilter(filterrul)

#Do some action in a Transaction
TransactionManager.Instance.EnsureInTransaction(doc)
for name,cat in zip(names,cats):
	paraele = ParameterFilterElement.Create(doc,name,catids)
	paraele.SetElementFilter(fRule)
	Parafilele.append(paraele)
TransactionManager.Instance.TransactionTaskDone()

#Final output
OUT = Parafilele

You will see they are both throwing up a similar casting error (shows the error is due to me not understanding casting or how to change types) on each node so its tripping basically at the very start but I’m hoping the rest of it that I have written should be fine?

Like I mentioned above in the future I would like to also add a bool input to either of the nodes/methods to toggle whether it was “AND or OR”.

If anyone could help me understand how to go forwards with the python code or any provide comments around the casting that would be great!

I have attached the dynamo graph I’m using a test trying to write the python nodes. It requires at least one wall in the project for it to get the parameter to feed in.
TEST_FILTER_CREATION.dyn (27.5 KB)