Auto-updating field in CorelDraw
Tags: vba, coreldraw, corel, technicaldrawing
Published: 2021-02-17 22:35:30

It is common feature of several applications to have so-called _fields_: small chunk of text that shows contestual data. Common examples are current date, number of page or file name: thigs that we often print in header or footer of documents.
This is a functionality so commond that we take it for granted in all applications.

On great use of them is to auto update the _Title block_ in technical drawings.
Below a common example of a block containing date, filename and layout name: all these data are predefined fields in applications such as AutoCAD, so it's very easy to add them.

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/8ncvk47jig6s0gpxf68g.png)

In other design software these fields does not exists, so it is necessary to came up with a custom solution. In this case I will replicate the behaviour of a AutoCAD Title block in CorelDraw. I am going to use VBA so the same logic might apply to other applications with the appropriate modification to syntax.

## When to run it
First of all it is necessary to decide when to trigger the update. I resolved to do this right before saving and printing. This way the data on the block are updated in the stored version of the file and on paper.

So, in the VBA editor, I modified the `BeforeSave` and `BeforePrint` events:

```vb
Private Sub Document_BeforePrint()
    Call UpdateTextFields
End Sub

Private Sub Document_BeforeSave(ByVal SaveAs As Boolean, ByVal FileName As String)
    Call UpdateTextFields
End Sub
```
## The function
<!--```vb
Private Sub UpdateTextFields()
    Dim CurrPage As Page
    Dim CurrShape As Shape
    
    For Each CurrPage In ActiveDocument.Pages
        Set CurrShape = CurrPage.Shapes.FindShape("TextDate")
        If Not CurrShape Is Nothing Then
            CurrShape.Text.Story = Format(DateTime.Now, "Short Date")
        End If
        Set CurrShape = CurrPage.Shapes.FindShape("TextPageName")
        If Not CurrShape Is Nothing Then
            CurrShape.Text.Story = CurrPage.Name
        End If
        Set CurrShape = CurrPage.Shapes.FindShape("TextFileName")
        If Not CurrShape Is Nothing Then
            CurrShape.Text.Story = ActiveDocument.FileName
        End If
    Next
End Sub
```-->
The first step is to store the names of the field in an array of string.
Then the procedure iterates among all the pages to search for the appropriate text boxes in the whole document.
Once found one of the box, the content is updated according to the name (and, by extension, to the type) of the box.
Here's the full code:

```vb
Private Sub UpdateTextFields()
    Dim CurrPage As Page
    Dim CurrShape As Shape
    Dim Texts(2) As String
    Dim CurrText As Variant
    Dim Output As String
    
    Texts(0) = "TextDate"
    Texts(1) = "TextPageName"
    Texts(2) = "TextFileName"
    
    For Each CurrPage In ActiveDocument.Pages
        For Each CurrText In Texts
            Set CurrShape = CurrPage.Shapes.FindShape(CurrText)
            If Not CurrShape Is Nothing Then
                Select Case CurrText
                    Case Texts(0)
                        Output = Format(DateTime.Now, "Short Date")
                    Case Texts(1)
                        Output = CurrPage.Name
                    Case Texts(2)
                        Output = ActiveDocument.FileName
                End Select
                CurrShape.Text.Story = Output
            End If
        Next
    Next
End Sub
```
The function looks in all the document's pages the three textbox named as in the array. If the text exists, then it will replace the content with the proper value.conta

Apart from the obvious code, a point of interest here is the property `Text.Story` that actually contains the text.