Create project parameters

from Autodesk.Revit.DB import*
from pyrevit import DB, forms, script, revit

import clr
clr.AddReference("RevitServices")
import RevitServices
from RevitServices.Persistence import DocumentManager 




# get ui doc and open views
app = __revit__.Application
doc = revit.doc
uidoc = revit.uidoc



def add_parameter_to_project(parameter_name):
    # Check if the parameter already exists
    existing_parameter = doc.ParameterBindings.get_Item(parameter_name)
    if existing_parameter is not None:
        print("The parameter '{parameter_name}' already exists.")
        return

    # Create a new shared parameter
    shared_parameter = ParameterFilterElement.CreateSharedParameterElement(doc, parameter_name, BuiltInParameter.INVALID, True)

    # Bind the parameter to the project
    category = Category.GetCategory(doc, BuiltInCategory.OST_GenericModel)  # You can change the category as needed
    binding = DefinitionBindingMap.Create(doc)
    binding.Insert(category.Id, shared_parameter.GetDefinition(), BuiltInParameterGroup.PG_DATA)

    # Apply the binding to the project
    doc.ParameterBindings.Insert(shared_parameter.GetDefinition(), binding, BuiltInParameterGroup.PG_DATA)

    print("The parameter '{parameter_name}' has been added to the project.")

# Specify the parameter name you want to add
parameter_name_to_add = "height"

# Call the function to add the parameter
add_parameter_to_project(parameter_name_to_add)

" I just created this script for project parameters, not solved . what is the problem this script and what is the solution?

@shuvro.arc ,

at the first view you have no transaction. So you need it, because it is a change in your current document.

f.e.

# 🔓 create project parameter
t = Transaction(doc, "create project parameter")
t.Start()
# try to create the parameter
t.Commit()
# 🔒 done

or leveraging the pyrevit revit module for transaction

from pyrevit import revit
# ---
with revit.Transaction(doc, "create param"):
    # do stuff

Thanks, but not solved.

from Autodesk.Revit.DB import*
from pyrevit import DB, forms, script, revit

import clr
clr.AddReference("RevitServices")
import RevitServices
from RevitServices.Persistence import DocumentManager 




# get ui doc and open views
app = __revit__.Application
doc = revit.doc
uidoc = revit.uidoc

# Specify the parameter name you want to add
parameter_name_to_add = "height"


with Transaction(doc, "P") as t:
    t.Start()
    # Check if the parameter already exists
    existing_parameter = doc.ParameterBindings.get_Item(parameter_name_to_add)
    if existing_parameter is not None:
        print("The parameter '{parameter_name}' already exists.")



    # Create a new shared parameter
    shared_parameter = ParameterFilterElement.CreateSharedParameterElement(doc, parameter_name_to_add, BuiltInParameter.INVALID, True)

    # Bind the parameter to the project
    category = Category.GetCategory(doc, BuiltInCategory.OST_GenericModel)  # You can change the category as needed
    binding = DefinitionBindingMap.Create(doc)
    binding.Insert(category.Id, shared_parameter.GetDefinition(), BuiltInParameterGroup.PG_DATA)

    # Apply the binding to the project
    doc.ParameterBindings.Insert(shared_parameter.GetDefinition(), binding, BuiltInParameterGroup.PG_DATA)

    print("The parameter '{parameter_name}' has been added to the project.")

    t.Commit()

" already aplied, but not solved. error message is (
image

ok. thanks. i will try it.

  • ParameterFilterElement does not have a ‘CreateSharedParameterElement’ method. Is this a function defined elsewhere in the code? See class here: ParameterFilterElement Methods

  • If you use the ‘with’ transaction syntax you don’t need to start/commit it. It will be freed from memory once it is finished with (commited) by pyRevit’s implementation of this class

I’m wondering if you’re trying to do this instead?

The code will likely only work if you actually have an existing shared parameter to get the external definition of to apply to that method if so.

Can’t help but feel the code might be GPT generated as some of it doesn’t seem to make sense or use valid API methods.

1 Like

Hi @shuvro.arc

You’re mixing the two suggestion, you should pick one or the other.

Since you import everything from Autodesk.Revit.DB, and you don’t fully qualify the pyrevit transaction with with revit.Transaction..., the transaction object used is the revit api one, which doesnt support the usage as context manager (the with keyword).

Use the with revit.Transaction as instructed by @Jean-Marc, and drop the t.Start() and t.Commit() since they are taken care by the pyrevit transaction itself (thats why I always suggest to use that, but nobody listen to me :sweat_smile:)

2 Likes

The only real benefit to using start/commit is when dealing with transaction groups in my xp or if you write your code for use elsewhere than pyRevit also (e.g. Dynamo). I’m pretty sure the ‘with’ transactions might not be able to assimilate with transaction groups as they might be disposed by the custom class. Haven’t checked, but otherwise the ‘with’ approach is far superior syntactically for sure.

Thanks for suggestions.

Hey @shuvro.arc , I don’t know if you have found the solution to your problem. I have recently noticed you post and I came with this script as a solution to add shared parameters to the project. It works for one paramater to one category as well as multiple parameter to multiple parameters.

# -*- coding: utf-8 -*-
# Created by Vasile Corjan
import System
from System import Enum
from pyrevit import forms, script, DB, revit
from category_lists import category_names_type, category_names_instance, built_in_parameter_group

# Get all categories and built-in parameter groups
app = __revit__.Application
doc = revit.doc
all_categories = [category for category in doc.Settings.Categories]
built_in_parameter_groups = [group for group in System.Enum.GetValues(DB.BuiltInParameterGroup)]
built_in_parameter_group_names = [DB.LabelUtils.GetLabelFor(n) for n in built_in_parameter_groups]

# Get the shared parameter file and its groups
sp_file = app.OpenSharedParameterFile()
sp_groups = sp_file.Groups
dict_pg = {g.Name:g for g in sp_groups}

# Select the parameter group
parameter_groups_dict = forms.SelectFromList.show(sorted(dict_pg),
                                        title='Select the Parameter Group',
                                        multiselect=False,
                                        button_name='Select')
if not parameter_groups_dict:
	script.exit()

# Select the parameter
definitions = dict_pg.get(parameter_groups_dict).Definitions
parameter_definitions_dict = {d.Name:d for d in definitions}
selected_parameters_names = forms.SelectFromList.show(sorted(parameter_definitions_dict),
                                        title='Select the Parameter',
                                        multiselect=True,
                                        button_name='Select')
if not selected_parameters_names:
	script.exit()
    
parameter_definitions = [parameter_definitions_dict.get(s) for s in selected_parameters_names]

# Select the built-in parameter group
selected_parameters = forms.SelectFromList.show(sorted(built_in_parameter_group),
                                        title='Select the parameters',
                                        multiselect=False,
                                        button_name='Select')
                                        
if selected_parameters in built_in_parameter_group_names: 
    parameter = built_in_parameter_groups[built_in_parameter_group_names.index(selected_parameters)]
else:
    None

# Select the binding type (Type or Instance)
bindings = ["Type","Instance"]
selected_binding = forms.SelectFromList.show(bindings,
                                        title='Select the binding type',
                                        multiselect=False,
                                        button_name='Select')
if not selected_binding:
    script.exit()
# Get the category names based on the selected binding type
if selected_binding == "Type":
    category_names = sorted(category_names_type)
else:
    category_names = sorted(category_names_instance)

selected_categories = forms.SelectFromList.show(category_names,
                                              title='Select the category',
                                              multiselect=True,
                                              button_name='Select')
if not selected_categories:
    script.exit()
categories = [c for c in all_categories if c.Name in selected_categories]
built_in_categories = [bic.BuiltInCategory for bic in categories]

# Adding the parameter
with revit.Transaction("Add Parameter"):
    category_set = app.Create.NewCategorySet()
    for bic in built_in_categories:
        category_set.Insert(DB.Category.GetCategory(doc,bic))
    if selected_binding == "Type":
        binding = app.Create.NewTypeBinding(category_set)
    else:
        binding = app.Create.NewInstanceBinding(category_set)
    for param_def in parameter_definitions:
        doc.ParameterBindings.Insert(param_def, binding, parameter)

Also I have done the work to filter the categories based on type/instance parameter in a separate file.

category_names_type = ["Air Terminals", "Analytical Links","Analytical Pipe Connections","Assemblies", "Audio Visual Devices","Cable Tray Fittings", "Cable Tray Runs", "Cable Trays", "Casework", "Ceilings", "Columns", "Communication Devices", "Conduit Fittings", "Conduit Runs", "Conduits", "Curtain Panels", "Curtain Systems", "Curtain Wall Mullions", "Data Devices", "Detail Items", "Doors", "Duct Accessories", "Duct Fittings", "Duct Insulations",
 "Duct Linings", "Duct Placeholders", "Duct Systems", "Ducts", "Electrical Equipment", "Electrical Fixtures", "Entourage", "Fire Alarm Devices", "Fire Protection", "Flex Ducts", "Flex Pipes", "Floors", "Food Service Equipment", "Furniture", "Furniture Systems", "Generic Models", "Grids", "Hardscape", "Levels", "Lighting Devices", "Lighting Fixtures","Mass", "Mechanical Control Devices", "Mechanical Equipment", "Mechanical Equipment Sets", "Medical Equipment", "MEP Fabrication Containment", "MEP Fabrication Ductwork", "MEP Fabrication Hangers", "MEP Fabrication Pipework", "Model Groups", "Nurse Call Devices", "Parking", 
 "Pipe Accessories", "Pipe Fittings", "Pipe Insulations", "Pipe Placeholders", "Pipes", "Piping Systems", "Planting", "Plumbing Equipment", "Plumbing Fixtures", "RVT Links", "Railings", "Ramps", "Rebar Shape", "Roads", "Roofs", "Security Devices", "Signage", "Site", "Specialty Equipment", "Sprinklers", "Stairs", "Structural Area Reinforcement", "Structural Beam Systems", "Structural Columns", "Structural Connections", "Structural Fabric Areas", "Structural Fabric Reinforcement", "Structural Foundations", "Structural Framing", "Structural Path Reinforcement", "Structural Rebar", "Structural Rebar Couplers", "Structural Stiffeners", "Structural Trusses", "Telephone Devices", "Temporary Structures", "Topography", "Vertical Circulation", "Walls", "Windows", "Wires"]
 
category_names_instance = ["Air Systems", "Air Terminals", "Analytical Links", "Analytical Members", "Analytical Nodes", "Analytical Openings", "Analytical Panels", "Analytical Pipe Connections", "Analytical Spaces", "Analytical Surfaces", "Areas", "Assemblies", "Audio Visual Devices",
 "Cable Tray Fittings", "Cable Tray Runs", "Cable Trays", "Casework", "Ceilings", "Columns", "Communication Devices", "Conduit Fittings", "Conduit Runs", "Conduits", "Curtain Panels", "Curtain Systems", "Curtain Wall Mullions", "Data Devices", "Detail Items", "Doors",
 "Duct Accessories", "Duct Fittings", "Duct Insulations", "Duct Linings", "Duct Placeholders", "Duct Systems", "Ducts", "Electrical Analytical Bus", "Electrical Analytical Loads", "Electrical Analytical Power Source", "Electrical Analytical Transfer Switch",
 "Electrical Analytical Transformer", "Electrical Circuits", "Electrical Equipment", "Electrical Fixtures", "Electrical Load Areas", "Entourage", "Fire Alarm Devices", "Fire Protection", "Flex Ducts", "Flex Pipes", "Floors", "Food Service Equipment", "Furniture", "Furniture Systems", "Generic Models", "Grids", "HVAC Zones", "Hardscape", "Levels", "Lighting Devices", "Lighting Fixtures", "MEP Fabrication Containment", "MEP Fabrication Ductwork", "MEP Fabrication Hangers", "MEP Fabrication Pipework", "Mass", "Materials", "Mechanical Control Devices", "Mechanical Equipment", "Mechanical Equipment Sets", "Medical Equipment", "Model Groups", "Nurse Call Devices", "Parking", "Parts", "Pipe Accessories", "Pipe Fittings", "Pipe Insulations", "Pipe Placeholders", "Pipes", "Piping Systems", "Planting", "Plumbing Equipment", "Plumbing Fixtures", "Project Information", "RVT Links", "Railings", "Ramps", "Rebar Shape", "Roads", "Roofs", "Rooms", "Schedules", "Security Devices", "Shaft Openings", "Sheets", "Signage", "Site", "Spaces", "Specialty Equipment", "Sprinklers", "Stairs", "Structural Area Reinforcement", "Structural Beam Systems", "Structural Columns", "Structural Connections", "Structural Fabric Areas", "Structural Fabric Reinforcement", "Structural Foundations", "Structural Framing", "Structural Path Reinforcement", "Structural Rebar", "Structural Rebar Couplers", "Structural Stiffeners", "Structural Trusses", "Switch System", "System-Zones", "Telephone Devices", "Temporary Structures", "Topography", "Vertical Circulation", "Views", "Walls", "Water Loops", "Windows", "Wires", "Zone Equipment"]

built_in_parameter_group = ["Analysis Results", "Analytical Alignment", "Analytical Model", "Constraints", "Construction",
"Data", "Dimensions", "Division Geometry", "Electrical", "Electrical - Circuiting", "Electrical - Lighting", "Electrical - Loads",
"Electrical Analysis", "Fire Protection", "Forces", "General", "Graphics", "Green Building Properties", "Identity Data",
"IFC Parameters", "Layers", "Life Safety", "Materials and Finishes", "Mechanical", "Mechanical Flow", "Mechanical Loads",
"Model Properties", "Moments", "Other", "Overall Legend", "Phasing", "Photometrics", "Plumbing", "Primary End", "Rebar Set", "Releases / Member Forces",
"Secondary End", "Segments and Fittings", "Set", "Slab Shape Edit", "Structural", "Structural Analysis", "Text", "Title Text", "Visibility"]

I hope it will be useful! :blush:

3 Likes

Thanks, it worked. nice work.

question, is there a way to create a project parameter directly without setting up an interim shared parameter? I am dealing with a simpler script that I need to create a parameter (Text, Rooms Category, Instance Binding) and I don’t want to be involved with SP.s

I guess this will answer your question.

1 Like

Haha !!, I knew it has something to do with API limitation, people were complaining about it since the good days of the world!
Thank you @Vasile_Corjan for clarification.

1 Like