Revit Parameter has a lot of relevant information such as group, type, unit, storage type, shared or native/built-in, read only or writable, and the most important ones, name, value and id (BuiltInParameter value or GUID), but they are scattered around in a few different API objects such as the Definition (which has two derivatives, InternalDefinition and ExternalDefinition, to address different kinds of Parameter instances).
In this post, let’s see how to collect all these pieces of information from an Element and put them together into a good place to make it ready to use for any possible purposes.
The following VB.NET code can find all the information from a selected Element:
Dim element As Autodesk.Revit.DB.Element = SelectElement(cmdData.Application.ActiveUIDocument.Selection).Element
Dim paramList As List(Of Parameter) = (From p In element.Parameters Select p)
Dim str As String = String.Empty
For Each p As Parameter In paramList
'The following has to be done because the DUT will throw out exceptions many times!
Dim unitType As String = String.Empty
Try
unitType = p.DisplayUnitType.ToString()
Catch
End Try
str += String.Format("{0}" & vbTab & "PG:{1}" & vbTab & "PT:{2}" & vbTab & "ST:{3}" & vbTab & "DUT:{4}" & vbLf & vbTab & "SH:{5}" & vbTab & "ID:{6}" & vbTab & "RO:{7}" & vbLf, p.Definition.Name, p.Definition.ParameterGroup, p.Definition.ParameterType, p.StorageType, unitType, _
p.IsShared, If(p.IsShared, p.GUID.ToString(), TryCast(p.Definition, InternalDefinition).BuiltInParameter.ToString()), p.IsReadOnly)
Next
MessageBox.Show(str, "Information of Element Parameters")
As commented in the code, the DisplayUnitType property of the Parameter object looks very special. It throws out exceptions very often and this will interrupt the whole process. The only way for programmers to address the issue is to use a try/catch block as demonstrated but that is definitely not something so cool. It is somewhat due to the fact that the DisplayUnitType enumeration lacks a value to indicate that DisplayUnitType does not make any sense in some situations just like the INVALID value in the BuiltInParameterGroup enumeration or Invalid in ParameterType.
Anyway we have a way to work around the issue and the above code can successfully print out the Parameter information like:
As mentioned earlier, we’d like to have a nice place to keep all the information so that we can use it in an easy way when necessary. The following help classes and methods will store all the Parameter information of an Element into a List of an informative object:
Public Class ParameterInfo
Public Property Name() As String
Get
Return m_Name
End Get
Set(ByVal value As String)
m_Name = Value
End Set
End Property
Private m_Name As String
Public Property Value() As String
Get
Return m_Value
End Get
Set(ByVal value As String)
m_Value = Value
End Set
End Property
Private m_Value As String
Public Property Group() As BuiltInParameterGroup
Get
Return m_Group
End Get
Set(ByVal value As BuiltInParameterGroup)
m_Group = Value
End Set
End Property
Private m_Group As BuiltInParameterGroup
Public Property Type() As ParameterType
Get
Return m_Type
End Get
Set(ByVal value As ParameterType)
m_Type = Value
End Set
End Property
Private m_Type As ParameterType
Public Property Storage() As StorageType
Get
Return m_Storage
End Get
Set(ByVal value As StorageType)
m_Storage = Value
End Set
End Property
Private m_Storage As StorageType
Public Property Unit() As String
Get
Return m_Unit
End Get
Set(ByVal value As String)
m_Unit = Value
End Set
End Property
Private m_Unit As String
'DisplayUnitType doesn't work!
Public Property [Shared]() As Boolean
Get
Return m_Shared
End Get
Set(ByVal value As Boolean)
m_Shared = Value
End Set
End Property
Private m_Shared As Boolean
Public Property ID() As String
Get
Return m_ID
End Get
Set(ByVal value As String)
m_ID = Value
End Set
End Property
Private m_ID As String
Public Property [ReadOnly]() As Boolean
Get
Return m_ReadOnly
End Get
Set(ByVal value As Boolean)
m_ReadOnly = Value
End Set
End Property
Private m_ReadOnly As Boolean
End Class
Public Shared Function GetParametersInfo(ByVal e As Autodesk.Revit.DB.Element) As List(Of ParameterInfo)
Dim paramList As List(Of ParameterInfo) = (From p In e.Parameters Select New ParameterInfo() With { _
.Name = p.Definition.Name, _
.Value = p.AsValueString(), _
.Group = p.Definition.ParameterGroup, _
.Type = p.Definition.ParameterType, _
.Storage = p.StorageType, _
.Unit = GetDUTString(p), _
.Shared = p.IsShared, _
.ReadOnly = p.IsReadOnly, _
.ID = If(p.IsShared, p.GUID.ToString(), TryCast(p.Definition, InternalDefinition).BuiltInParameter.ToString()) _
}).ToList()
Return paramList
End Function
Public Shared Function GetDUTString(ByVal p As Parameter) As String
Dim unitType As String = String.Empty
Try
unitType = p.DisplayUnitType.ToString()
Catch
End Try
Return unitType
End Function
And the following code will convert the informative object List into a single string:
Public Function ParametersInfoToCSVString(ByVal infoList As List(Of ParameterInfo), ByRef title As String) As String
Dim sb As New StringBuilder()
Dim propInfoArrary As PropertyInfo() = GetType(ParameterInfo).GetProperties()
For Each pi As PropertyInfo In propInfoArrary
title += pi.Name + ","
Next
title = title.Remove(title.Length - 1)
For Each info As ParameterInfo In infoList
For Each pi As PropertyInfo In propInfoArrary
Dim obj As Object = info.GetType().InvokeMember(pi.Name, BindingFlags.GetProperty, Nothing, info, Nothing)
sb.Append((If(obj Is Nothing, String.Empty, obj.ToString())) & ",")
Next
sb.Remove(sb.Length - 1, 1).Append(Environment.NewLine)
Next
Return sb.ToString()
End Function
Then we can write all the Parameter information of a selected Element to a CSV file, for example:
Public Shared Function SelElement(ByVal selection As Autodesk.Revit.UI.Selection.Selection) As Reference
Dim picked As Reference = selection.PickObject(Autodesk.Revit.UI.Selection.ObjectType.Element, "Please select an element")
Return picked
End Function
…
Dim element As Autodesk.Revit.DB.Element = SelElement(cmdData.Application.ActiveUIDocument.Selection).Element
Dim paramsInfo As List(Of ParameterInfo) = GetParametersInfo(element)
Using sw As New StreamWriter("c:\ParametersInfo.csv")
Dim title As String = String.Empty
Dim rows As String = ParametersInfoToCSVString(paramsInfo, title)
sw.WriteLine(title)
sw.Write(rows)
End Using
…
Finally the CSV file can be read into a spreadsheet of Excel for example:
The informative object list can be used for any other purposes as well for sure.
Parameter Infoer of RevitAddinWizard can help do all of these in a configurable and flexible way either in C# or VB.NET depending on what language of the current project is.
Recent Comments