Acceso a la API de Revit con Dynamo y Python, Dyna-Thon


acceso-a-la-api-de-revit-con-dynamo-y-python

“Sabemos con certeza sólo cuando sabemos poco; con el conocimiento aumenta la duda”

Goethe.

Dynamo de Ian Keoug, es una excelente herramienta que nos permite programar en Revit sin escribir líneas de código. Sin embargo a veces no encontraremos un nodo que haga justo lo que necesitamos, si te ha pasado esto seguro un Dyna-Thon (así llamo al nodo Python script) es lo que necesitas, lo que logramos con esto es el acceso a la API de Revit con Dynamo y Python.

¿Qué es la API de Revit?

API es el acrónimo para “Programming Application Interface“, en español “Interfaz de Programación de Aplicaciones“. Es un conjunto de métodos y especificaciones que las aplicaciones pueden usar para comunicarse entre sí. Funcionado así, como su nombre lo indica, como una interfaz entre distintos programas. Del mismo modo en que una interfaz de usuario facilita la interacción entre el humano y la aplicación.

Revit ofrece un kit de desarrollo de software (SDK) que incluye la documentación requerida para hacer uso de la API. Afortunadamente esta documentación también la encontramos en la web en la página apidocs gracias a Gui Talarico. Aquí puedes apoyar al proyecto Apidocs.co

Así las cosas, por un lado tenemos la interfaz de usuario de Revit que nos ofrece una cantidad limitada de comandos para desarrollar y gestionar nuestros modelos. Y por el otro la interfaz de la aplicación (API). Que si ya has visitado apidocs y has checado la documentación de tu versión de Revit, podrás ver la cantidad de elementos que contiene. Pues bien, es con estos elementos con los que podemos crear nuevos flujos de trabajo y ampliar la funcionalidad de Revit.

Revit API, Interfaz de Programación de la Aplicación

Python Script (Dyna-Thon)

Este nodo lo encontramos desplegando la Categoría “Scripts” y Subcategoría “Editor” de Dynamo y viene por defecto al instalar cualquier versión de este. Al dar doble click sobre el nodo se abrirá el editor de código Python que contiene ya varias líneas de código. A estas líneas de código que van al inicio se les suele llamar “Boiler Plate code“.

Dyna-Thon, acceso a la API de Revit

Boilerplate Code o Código repetitivo

Esta sección de código es de lo más importante, sin estas líneas tu script simplemente no funcionará puesto que aquí es donde cargamos las librerías y recursos necesarios para trabajar con la base de datos de nuestros modelos.

En la página Dynamo Python Primer podemos encontrar un ejemplo que podemos usar como plantilla para la mayoría de nuestros scripts. Es importante tratar de entender que es lo que hace cada línea de código. También debemos tener en cuenta que NO es lo más recomendable cargar siempre todas estas líneas por que estaremos cargando demasiados elementos que no se estarán utilizando en el desarrollo de nuestro código y solo ralentizará el tiempo de ejecución del mismo.

Aquí te dejo el Bolierplate code con la traducción de las anotaciones para cada línea de código.

Bolierplate code, acceso-a-la-api-de-revit-con-dynamo-y-python
import clr #.NET's Common Language Runtime. Es un entorno de ejecución
#capaz de ejecutar código de distintos lenguajes.
import sys #sys Es una importante librería de Python - que usamos para cargar
#las librerías estándar de IronPython.
sys.path.append('C:\Program Files (x86)\IronPython 2.7\Lib') #Importa las
#Librerías estándar de IronPython cubriendo desde servidores y
#encriptación hasta expresiones regulares.
import System #Namespaces del Sistema en el entorno .NET
from System import Array #Clase .NET para manejar información de matrices
from System.Collections.Generic import * #Te permite manejar "generics". A veces la API de Revit
#listas rígidas "genericas", llamadas ILists. Si no las necesitas
#puedes eliminar esta línea.
clr.AddReference('ProtoGeometry')  #Librería de Dynamo para sus Clases de Geometría
#Sólo la necesitarás si estás interactuando con geometrías.
from Autodesk.DesignScript.Geometry import * #Carga todo de la librería
#de Geometría de Dynamo.
clr.AddReference("RevitNodes") #Nodos de Dynamo para Revit
import Revit #Carga el Namespace Revit en los RevitNodes.
clr.ImportExtensions(Revit.Elements) #Carga más librerías Revit de Dynamo.
clr.ImportExtensions(Revit.GeometryConversion) #Carga más librerías Revit de Dynamo
#Sólo la necesitarás si estás interactuando con geometrías.
clr.AddReference("RevitServices") #Clases de Dynamo para manejo de Documentos Revit
import RevitServices 
from RevitServices.Persistence import DocumentManager #Clase interna de Dynamo
#que rastrea el documento en el cuál se está ejecutando
from RevitServices.Transactions import TransactionManager #Clase de Dynamo para
#abrir y cerrar transacciones que modifican la base de datos del documento Revit.
clr.AddReference("RevitAPI") #Referencia a las DLLs de la API de Revit.
clr.AddReference("RevitAPIUI") #Referencia a las DLLs de la API de Revit.

import Autodesk #Carga el Namespace Autodesk.
from Autodesk.Revit.DB import * #Carga todas las clases de la API de Revit.
from Autodesk.Revit.UI import * #Carga todas las clases de la API UI de Revit.  

doc = DocumentManager.Instance.CurrentDBDocument #Configura el manejo del documento activo de Revit.
uiapp = DocumentManager.Instance.CurrentUIApplication #Configura el manejo de la UI del documento activo de Revit.
app = uiapp.Application  #Configura el manejo de la sesión activa de Revit.
uidoc = uiapp.ActiveUIDocument #Configura el manejo de la UI de la sesión activa de Revit.

Como puedes ver son sólo dos líneas las que llaman a la API de Revit:

  • clr.AddReference(“RevitAPI”)
  • clr.AddReference(“RevitAPIUI”)

Ejemplo, usando Dyna-Thon y Apidocs.co

Realizaremos un ejercicio sencillo donde desarrollaremos un nodo Dyna-Thon para conseguir acceso a la API de Revit con Dynamo y Python, y usar un comando de la API de Revit llamado “FilteredElementCollector“. Con este comando o “Clase” lo que hacemos es aplicar filtros para trabajar solo con los elementos deseados.

En este ejemplo vamos a filtrar las notas de texto de nuestro modelo para cambiarlas de minúsculas a mayúsculas.

El primer paso será buscar la Clase “FilteredElementCollector” con el buscador de Apidocs.

FilteredElementCollector Clase

Al dar click sobre el nombre de la Clase se abre la ficha con información valiosa como una descripción de que podemos hacer con este elemento, el Namespace al que pertenece “Autodesk.Revit.DB“, lo cuál es muy importante por que así sabemos desde donde importar esta Clase. “from Autodesk.Revit.DB import FilteredElementCollector”.

Bajo el nombre de la Clase podemos ver el apartado “Members” donde podemos explorar que métodos nos permite usar esta Clase, en este ejemplo usaremos 3 de estos métodos.

FilteredElementorCollector Métodos

En el siguiente diagrama podemos ver de que manera se estructura la Clase “FilteredElementCollector“, que deriva en Constructores y Métodos, son los métodos los que generalmente nos servirán para manipular y modificar información de la base de datos del modelo.

FilteredElementCollector Estructura
Diagrama de la Clase_FilteredElementCollector

Ya que conocemos los métodos que vamos a utilizar para filtrar las notas de texto podemos escribir las líneas de código en el editor de Python.

FilteredElementCollector

Dynamo Transaction Manager, abrir y cerrar Transacciones

Cuando ejecutamos acciones que sobrescriben la base de datos del modelo, como mover, agregar, eliminar o modificar propiedades de elementos necesitamos realizar una “Transacción“. Para esto Dynamo nos ofrece un Administrador de Transacciones o “Transaction Manager” que ya hemos cargado en una de las líneas del Boilerplate code al inicio. Usaremos dos métodos del Transaction Manager, uno para “Abrir” la transacción y otro para “Cerrarla“, entre estos dos métodos escribiremos las líneas de código que harán la modificación de nuestros elementos.

Transaction Manager
import clr

clr.AddReference("RevitNodes")
import Revit 

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

clr.AddReference("RevitAPI")
clr.AddReference("RevitAPIUI")

# Este codigo se comparte en https://bimetheca.com

from Autodesk.Revit.DB import FilteredElementCollector, BuiltInCategory


doc = DocumentManager.Instance.CurrentDBDocument
uiapp = DocumentManager.Instance.CurrentUIApplication 
app = uiapp.Application 
uidoc = uiapp.ActiveUIDocument


all_text = FilteredElementCollector(doc)# Usamos la Clase para empezar a filtrar
all_text.OfCategory(BuiltInCategory.OST_TextNotes)# Filtramos por categoría "Text Notes"
all_text.WhereElementIsNotElementType()# Filtramos elementos que NO sean tipos.
all_text.ToElements()# Nos devuelve el conjunto de elementos que pasaron los filtros

# Para abrir una nueva transacción, necesitamos usar la Clase Transaction Manager
# Que toma como único argumento el documento actual "doc"
TransactionManager.Instance.EnsureInTransaction(doc)

# Iteramos sobre cada elemento del conjunto que filtramos con el "FilteredElementCollector"
# Y con el método .upper convertimos a mayúsculas las notas de texto
for el in all_text:
	el.Text = el.Text.upper()
	
# El siguiente método cerrará la transacción y confirmará
# los cambios hechos a la base de datos del modelo
TransactionManager.Instance.TransactionTaskDone()

Una vez realizada la transacción podemos cerrar el editor de código y ejecutar el script.

Dyna-Thon y Revit API, un mundo de posibilidades

Como puedes ver la API de Revit abre todo un mundo de posibilidades para quienes desean personalizar la funcionalidad del software. Y en combinación con Dynamo se consigue un flujo de trabajo excelente para tareas de automatización, si ya trabajas con los nodos de Dynamo es hora de que empieces a crear tus Dyna-Thons e integres la versatilidad de la programación por código con la facilidad de la programación visual.

Espero que el artículo Dyna-Thon, acceso a la API de Revit con Dynamo y Python te sea de utilidad y te anime a descubrir la utilidad de las APIs y las ventajas de saber un poco programación por código. Sientete con la libertad de comentarnos dudas o sugerencias para mejorar el contenido que te presentamos en Bimetheca. Y espera por nuevos artículos relacionados con este y otros temas que tenemos preparados para tí.

¡Hasta el próximo artículo!.


Gilberto Granados, Arquitecto y Modelador BIM en INSECOM

Términos y condiciones

El contenido proporcionado en Bimetheca es solo para fines informativos; el propietario de este blog no se responsabiliza de la exactitud, integridad y disponibilidad de la información de este sitio, el propietario no será responsable de ninguna pérdida, lesión o daño por la visualización o el uso de esta información.

Nos complace que compartan nuestras publicaciones a través de todas las plataformas de redes sociales; incluyendo las publicaciones originales con crédito al autor y proporcionando un enlace al contenido original.

Estos términos y condiciones de uso están sujetos a cambios en cualquier momento y sin previo aviso.