Jul 1, 2024

How To Purge View Templates with pyRevit

Learn how to purge View Templates in your Revit project with pyRevit.

Purge View Templates with EF-Tools

Before we dive into the code, I want you to know that you can use this tool in EF-Tools. You can even inspect the code by holding ALT and clicking on the button to open the location of the source code.

πŸ‘€But Now let's look at the code.

Brainstorming

This is a very simple tool.

We need to find all unused view templates and then ask user which ones to delete. I don't think that there is a method to get all unused in Revit API, so we will find all used view templates first, by iterating over all views, and then find the difference with all view templates.

Here are the steps we will go through:

  1. Get All Views and ViewTemplates

  2. Find Used ViewTemplates (iterate through views)

  3. Find all Unused ViewTemplates (set_A - set_B)

  4. Ask User Which ones to Delete (pyrevit.forms)

  5. Purge View Templates

1️⃣ Get View and ViewTemplates

First of all, you will need to get your Views and View Templates.
It's also a good idea to sort them accordingly.

#πŸ‘‰ Get Views and ViewTemplates
all_view_and_vt = FilteredElementCollector(doc).OfCategory(BuiltInCategory.OST_Views).WhereElementIsNotElementType().ToElements()
all_views       = [v for v in all_view_and_vt    if not v.IsTemplate]
all_vt_ids      = [v.Id for v in all_view_and_vt if     v.IsTemplate]

2️⃣ Get Used ViewTemplates

Now, we can iterate through all views and get ViewTemplateId.
Then, it's important to check that it's not ElementId(-1), because it refers to None in Revit API.

#πŸ”¬ Get Used ViewTemplates
used_vt_ids = []

for view in all_views:
    vt_id = view.ViewTemplateId
    if vt_id != ElementId(-1):
        if vt_id not in used_vt_ids:
            used_vt_ids.append(vt_id)

3️⃣ Get Unused ViewTemplates

We have all view templates, and a list of used view templates.

Now we can turn them into sets and subtract one from another to get the difference, which will be our unused View Templates

πŸ’‘ It's also a good idea to ensure we have unused templates.

# Get All Unused ViewTemplates
unused_vt_ids = set(all_vt_ids) - set(used_vt_ids)
unused_vts    = [doc.GetElement(vt_id) for vt_id in unused_vt_ids]

# βœ… Ensure Unused ViewTemplates
if not unused_vt_ids:
    forms.alert('There are no unused ViewTemplates in the project. Please try again.',title=__title__, exitscript=True)

4️⃣ Select ViewTemplates to Purge

Now it's time to give some control to our users.

We shouldn't delete all unused view templates; instead, we should ask them to select which ones to delete. 
We can use pyrevit.forms.SelectFromList to quickly create a list of our unused View Templates.

πŸ’‘Make sure the user has selected something here.

#πŸ”Ž Select ViewTemplates to Purge
vt_to_del = forms.SelectFromList.show(unused_vts,
                                multiselect=True,
                                name_attr='Name',
                                button_name='Select Unused ViewTemplates to Purge')

# βœ… Ensure ViewTemplates were selected
if not vt_to_del:
    forms.alert('There were no ViewTemplates Selected. Please try again.',title=__title__, exitscript=True)

5️⃣ Purge ViewTemplates

Finally, we can get rid of these unused view templates.

Overall, we just need to use doc.Delete method, but it's also good to add try/except in case these templates are used by other users or something else.

#πŸ”₯ Purge ViewTemplates
t = Transaction(doc, 'Purge ViewTemplates')
t.Start()  #πŸ”“

deleted = 0
for vt in vt_to_del:
    try:
        vt_name = vt.Name
        doc.Delete(vt.Id)
        output.print_md('πŸ”₯Purged ViewTemplate: **{}**'.format(vt_name))
        deleted += 1
    except Exception as e:
        print("βœ–οΈ Couldn't delete ViewTempalte: {} due to {}".format(vt_name, e))

t.Commit() #πŸ”’

✨Full Code

πŸ‘‡Here is the final code with all the steps together and also a few additional print statements.

y
# -*- coding: utf-8 -*-
__title__ = "Purge Unused View Templates"
__doc__ = """Version = 1.0
Date    = 24.06.2024
_____________________________________________________________________
Description:
Purge Unused View Templates from your Revit Project.
_____________________________________________________________________
How-To:
- Click the Button
- Select unused View Templates to purge
_____________________________________________________________________
Last update:
- [28.06.2024] - V1.0 RELEASE
_____________________________________________________________________
Author: Erik Frits from LearnRevitAPI.com"""

# ╦╔╦╗╔═╗╔═╗╦═╗╔╦╗╔═╗
# ║║║║╠═╝║ ║╠╦╝ β•‘ β•šβ•β•—
# β•©β•© β•©β•©  β•šβ•β•β•©β•šβ• β•© β•šβ•β• IMPORTS
# ==================================================
from Autodesk.Revit.DB import *

# pyRevit
from pyrevit import forms, script

# ╦  ╦╔═╗╦═╗╦╔═╗╔╗ ╦  ╔═╗╔═╗
# β•šβ•—β•”β•β• β•β•£β• β•¦β•β•‘β• β•β•£β• β•©β•—β•‘  β•‘β•£ β•šβ•β•—
#  β•šβ• β•© β•©β•©β•šβ•β•©β•© β•©β•šβ•β•β•©β•β•β•šβ•β•β•šβ•β• VARIABLES
# ==================================================
doc    = __revit__.ActiveUIDocument.Document
uidoc  = __revit__.ActiveUIDocument
output = script.get_output()

# ╔╦╗╔═╗╦╔╗╔
# ║║║╠═╣║║║║
# β•© β•©β•© β•©β•©β•β•šβ• MAIN
# ==================================================
#πŸ‘‰ Get Views and ViewTemplates
all_view_and_vt = FilteredElementCollector(doc).OfCategory(BuiltInCategory.OST_Views).WhereElementIsNotElementType().ToElements()
all_views       = [v for v in all_view_and_vt    if not v.IsTemplate]
all_vt_ids      = [v.Id for v in all_view_and_vt if     v.IsTemplate]


#πŸ”¬ Get Used ViewTemplates
used_vt_ids = []

for view in all_views:
    vt_id = view.ViewTemplateId
    if vt_id != ElementId(-1):
        if vt_id not in used_vt_ids:
            used_vt_ids.append(vt_id)

# Get All Unused ViewTemplates
unused_vt_ids = set(all_vt_ids) - set(used_vt_ids)
unused_vts    = [doc.GetElement(vt_id) for vt_id in unused_vt_ids]

# βœ… Ensure Unused ViewTemplates
if not unused_vt_ids:
    forms.alert('There are no unused ViewTemplates in the project. Please try again.',title=__title__, exitscript=True)

#πŸ”Ž Select ViewTemplates to Purge
vt_to_del = forms.SelectFromList.show(unused_vts,
                                multiselect=True,
                                name_attr='Name',
                                button_name='Select Unused ViewTemplates to Purge')

# βœ… Ensure ViewTemplates were selected
if not vt_to_del:
    forms.alert('There were no ViewTemplates Selected. Please try again.',title=__title__, exitscript=True)

#πŸ‘€ Print ViewTemplates Report
output.print_md('### There were {}/{} Unused ViewTemplates in the project.'.format(len(unused_vt_ids), len(all_vt_ids)))
output.print_md('---')

#πŸ”₯ Purge ViewTemplates
t = Transaction(doc, 'Purge ViewTemplates')
t.Start()  #πŸ”“

deleted = 0
for vt in vt_to_del:
    try:
        vt_name = vt.Name
        doc.Delete(vt.Id)
        output.print_md('πŸ”₯Purged ViewTemplate: **{}**'.format(vt_name))
        deleted += 1
    except Exception as e:
        print("βœ–οΈ Couldn't delete ViewTempalte: {} due to {}".format(vt_name, e))

t.Commit() #πŸ”’

#πŸ‘€ Create Final print statement
output.print_md('---')
output.print_md('*Script Execution has finished. {} ViewTemplates were purged.*'.format(deleted))

#⌨️ Happy Coding!

Join Newsletter

πŸ“© You will be added to Revit API Newsletter

Join Us!

which is already read by 7400+ people!

Ready to become Revit Hero for your office? Learn Revit API!

Join this comprehensive course that will guide you step by step on how to create your dream tools for Revit that save time.