Creat view filter for project parameter

Dear friends.:grinning:
I want use python code to create some filter, but when I test it aways with this warming :ofCategoryId() takes exactly 2 arguments (1 given)
But according to the revit api ofCategoryId() only need one given. Im a new for python and need some help from our forum. the blow picture is the the python code and I’ve tested it in the Revitpythonshell and Dynamo Python node.
Before many thanks to our friends and your help.

C

You need to supply the Document you are using it against. FilteredElementCollector (doc). OfCategoryId

Hi SeanP, Very appreciate for your help this problem is resovled.
:grinning:But here I meet another new problem, do you know how can get it.
The blow snopshot is collected information about new problem.

Take a look at this link, I think it will solve what you are looking for. The reason it that a “List” in python is not completely equivalent to an ICollection in the Revit API.

Hi, SeanP many many thanks for your help.
I’ve got this ICollection point.
But I still confuse in Revit parameter element, and here have warming see the below snapshot and script. I’m not sure para is used right or in here is wrong. Do you have any experience can share, many thanks again?


import Autodesk
from Autodesk.Revit.DB import *
import System
from System.Collections.Generic import *
doc = revit.ActiveUIDocument.Document

# Get category list of the project parameter
def _GetParamCat(param):

    # Collect parameter and category list
    params = []
    cats = []
    iterator = doc.ParameterBindings.ForwardIterator()
    while iterator.MoveNext():
    	params.append(iterator.Key.Name)
    	thesecats = []
    	for cat in iterator.Current.Categories:
    		thesecats.append(Category.GetCategory(doc,cat.Id))
    	cats.append(thesecats)

    #Return category list
    if param in params:
        return cats[params.index(param)]
    else:
        return ["%s is not a parameters name" %(param)]


def _CreatParamStrEqFilter(param):
    cats = _GetParamCat(param)

    #DB transaction
    tran = Transaction(doc,"Creat ID Filter")
    tran.Start()

    #Get parameter from parameter category List
    Elemcollector = []
    for i in cats:
        collector = FilteredElementCollector(doc).\
                    OfCategoryId(i.Id).\
                    WhereElementIsNotElementType().ToElements()
        Elemcollector.extend(collector)

    #Revit parameter PENDING
    '''
    collectortemp = FilteredElementCollector(doc).OfCategory(BuiltInCategory.OST_ProjectInformation).ToElements()
    for projPar in collectortemp:
        for parameter in projPar.Parameters:
            if parameter.Definition.Name == param:
                parR = parameter
                break
    '''
    #Get all parameter values PENDING
    pvalues = [""]
    for elem in Elemcollector:
        para = elem.LookupParameter(param)
        pvalues.append(para.AsString())
    pvalue = list(set(pvalues))

    #Creatd a new rule
    rulels = []
    for i in pvalue:
        rulels.append(ParameterFilterRuleFactory.CreateEqualsRule(para.Id,i,False))

    #Typed category list ------- Important!!!
    ids1 = list()
    for i in cats:
        ids1.append(i.Id)
    catlist = List[ElementId](ids1)

    rulelist = list()
    for i in rulels:
        rulelist.append(List[FilterRule]([i]))
    
    #Create parameter filter elmenets
    filters = []
    for i in pvalue:
        if len(i) == 0:
            name = 'Id - ' + i
        else:
            name = 'Id - Empty'
        filters.append(ParameterFilterElement.Create(doc,name,catlist,rulelist[pvalue.index(i)]))

    tran.Commit()
    
    return filters
    
a = _CreatParamStrEqFilter("ACTIVITY ID")
print a

The error message means you are trying to Apply a rule to a category that can’t have that rule. That isn’t a Python thing, that’s a Revit thing. I would try using the script on a simple list of one category, one rule, and one filter etc to see if it’s working. Then start to filter or define ways to make sure your inputs are valid.

1 Like

Hi, Sean many many thanks for your reply and help, tomorrow I will manage to resolve this issue. Today is too late:grinning:

I appreciate you and your time.:blush:

Hi SeanP
Here also with some question. If you have some time can you try the below code in revitpythonshell or dynamo.
import Autodesk
from Autodesk.Revit.DB import *
import System
from System.Collections.Generic import *
doc = revit.ActiveUIDocument.Document

param = "ACTIVITY ID"
# Get category list of the project parameter
def _GetParamCat(param):

    # Collect parameter and category list
    params = []
    cats = []
    iterator = doc.ParameterBindings.ForwardIterator()       #PENDING NEED TO STUDY MORE
    while iterator.MoveNext():
        if iterator.Key.Name == param:
        	params.append(iterator.Key.Name)
        	for cat in iterator.Current.Categories:
        		cats.append(Category.GetCategory(doc,cat.Id))
    return cats

#Got category of parameter
cats = _GetParamCat(param)

#DB transaction
tran = Transaction(doc,"Creat ID Filter")
tran.Start()

#Get parameter from parameter category List
Elemcollector = []
for i in cats:
    collector = FilteredElementCollector(doc).\
                OfCategoryId(i.Id).\
                WhereElementIsNotElementType().ToElements()
    Elemcollector.extend(collector)

#Get Revit parameter
paraRId = Elemcollector[0].GetParameters(param)[0].Id

#Get all parameter values PENDING
pvalues = []
for elem in Elemcollector:
    para = elem.LookupParameter(param)
    pvalues.append(para.AsString())
pvalue = list(set(pvalues))

#Creatd a new rule
rulels=ParameterFilterRuleFactory.CreateEqualsRule(paraRId,pvalue[0],False)

#Typed category list ------- Important!!!
ids1 = list()
for i in cats:
    ids1.append(i.Id)
catlist = List[ElementId](ids1)

filters = ParameterFilterElement.Create(doc,"TEST",catlist,List[FilterRule]([rulels]))

tran.Commit()

print filters

Now when I run it in the Revitpythonshell with the below warming, I try to fix it but still in here.

Hey my friends SeanP.
Many thanks for you. After some time and test, finally I get it, now the script is working~~:wink::grinning::star_struck::blush:

1 Like

Glad to hear it! Would you share your final working Python to support others efforts?

Hi, here is the python script. I think it can be useful in some situations, and this script can optimize to get bitter and fast speed~ Thank you agein~~~:grinning:
import Autodesk.
from Autodesk.Revit.DB import *
import System
from System.Collections.Generic import *
doc = revit.ActiveUIDocument.Document

# Get category list of the project parameter
def _GetParamCat(param):

    # Collect parameter and category list
    params = []
    cats = []
    iterator = doc.ParameterBindings.ForwardIterator()       #PENDING NEED TO STUDY MORE
    while iterator.MoveNext():
        if iterator.Key.Name == param:
        	params.append(iterator.Key.Name)
        	for cat in iterator.Current.Categories:
        		cats.append(Category.GetCategory(doc,cat.Id))
    return cats

# Creat view filter by different parameter value (value AsString)
def _CreatParamStrEqFilter(param):

    #Get category list of the parameter
    cats = _GetParamCat(param)

    #Collector elements of those categories
    Elemcollector = []
    for i in cats:
        collector = FilteredElementCollector(doc).\
                    OfCategoryId(i.Id).\
                    WhereElementIsNotElementType().ToElements()
        Elemcollector.extend(collector)

    #Get Revit parameter from a element that in collector
    paraRId = Elemcollector[0].GetParameters(param)[0].Id

    #Get all parameter values PENDING
    pvalues = []
    for elem in Elemcollector:
        para = elem.LookupParameter(param)
        pvalues.append(para.AsString())

    pvalue = list(set(pvalues))
    if None in pvalue:
        pvalue[pvalue.index(None)] = ''

    #Creatd a new rule
    rulels = []
    for i in pvalue:
        rulels.append(ParameterFilterRuleFactory.CreateEqualsRule(paraRId,i,False))

    #Typed category list ------- Important!!!
    ids1 = list()
    for i in cats:
        ids1.append(i.Id)
    catlist = List[ElementId](ids1)

    #Create parameter filter elmenets
    t = Transaction(doc,name)
    t.Start()

    filters = []
    for i in pvalue:
        if i == '':
            name = 'ID - EMPTY'
        else:
            name = 'ID - ' + i
        filters.append(ParameterFilterElement.Create(doc,name,catlist,List[FilterRule]([rulels[pvalue.index(i)]])))

    t.Commit()

    return filters
1 Like