This Client Server article is republished in its entirety from 2003 for reference purposes.
By Yuedong Bi, Developer Support Analyst, Bentley Corporate Office 05 May 2003
This article describes how to write a recursive routine to solve a complex problem by solving progressively simpler problems, until a final base case can be reached. There are many practical applications to apply the theory of recursion for any nested object in MicroStation objects such as cells, attachments, etc.
Recursive definitions are common in mathematics. Any series in which a term is defined using the values of earlier terms in the series is a recursive definition. For example, the sum of the first n integers can be defined as the value of n plus the sum of the first n-1 integers.
Here is a recursive function to compute this sum:
Function sumNumber (n As Integer) As Integer
If n <= 1 Then ‘Base case
sumNumber = 1
Else ‘ the recursive call
sumNumber = sumNumber(n - 1) + n
As illustrated above, you can see that a recursive function has two cases:
1. The base case - If the problem is simple enough, it is solved without recursive calls. In the above example, the sum of the 1st integer is 1.
2. The recursive call - The function calling itself to solve a simpler problem, as in the above example, would call itself by calculating the sum of the current n-1 integers.
As mentioned previously, a recursive function has many practical applications in MicroStation. For example, in the managing of nested cells, the base case is always a primitive element (such as line, shape, text, ellipse, etc.), which cannot be broken down to a simpler case to manage.
To change the color of a shape element, we can:
Dim oShapeElement As ShapeElement‘ ....... Get oShapeElement from scan,‘ user pick from model, or create oneoShapeElement.Color = 4 'Change element color‘rewrite changes to its model.oShapeElement.Rewrite ‘Redraws this object on the viewShapeElement.Redraw msdDrawingModeNormalTo change the font of a text element:
Dim oFont As FontSet oFont = ActiveDesignFile.Fonts(3)With oTextElement.TextStyle.Font = oFont.RewriteEnd WithTo process a cell element, the solution to apply would use an ElementEnumerator similar to:
Dim oElEnum As ElementEnumeratorSet oElEnum = oCellElement.GetSubElementsDo While oElEnum.MoveNext‘ ..... Process each element inside a cellLoop
In a recursive call, the function will keep calling itself to solve a simpler problem until the base case has been satisfied.
This code illustrates how a recursive function call is used to list all elements within a nested cell:
Function processNestedCell (oCellElement As _
CellElement) As Variant
Dim oElEnum As ElementEnumerator
Dim oSubElement As Element
Set oElEnum = oCellElement.GetSubElementsDo While oElEnum.MoveNext
Set oSubElement = oElEnum.Current
If oSubElement.Type = msdElementTypeCellHeader _
Debug.Print "Nested Cell Name: " & _ oSubElement.AsCellElement.Name
' Recursive call
' Base case, not a cell element,
‘ If needed, you can check more type,
' Such as if type is text or text node
‘ do something, ....
'More control on each type element.
‘Such as change Ellipse color
If oSubElement.Type = _
oSubElement.AsEllipseElement.Color = 4
'Change element color
Upon receiving a list of elements within a complex nested cell you can now easily manage and process each individual base case elements, performing any required operation such as changing the symbology or properties.
Note: If you are performing an operation that would attempt to change the size of a complex object it is recommended that you do not simply delete individual elements in cell. Instead, create a new cell with of the correct size and delete the old one.
Try taking these concepts further and see if you can use recursion to manage other complex element types in MicroStation such as reference files, etc.
Client Server Archive
MicroStation Desktop TechNotes and FAQs
Bentley's Technical Support Group requests that you please confine any comments you have on this Wiki entry to this "Comments or Corrections?" section. THANK YOU!
Please clean up and format the code.