There is a MS Word 2016 document with DOCVARIABLES set in it. For example:
{ DOCVARIABLE "SerialNumber" \* MERGEFORMAT }
I need to have this DOCVARIABLE filled in via VBA with InputBox. The VBA code:
Sub Document_Open()
Dim sNumber, mNumber, iDate As String
sNumber = InputBox("Please enter the Serial Number", "Serial number", "Enter
the Serial Number here")
mNumber = InputBox("Please enter the Model Number", "Model number", "Enter
the Model Number here")
iDate = InputBox("Please enter the Date of Issue, dd.mm.yyyy", "Date of
Issue", "Enter the Date of Issue here")
With ActiveDocument
.Variables.Add Name:="SerialNumber", Value:=sNumber
.Variables.Add Name:="ModelNumber", Value:=mNumber
.Variables.Add Name:="IssueDate", Value:=iDate
.Fields.Update
End With
End Sub
When the document opens up, it automatically prompts for user data. When the data is entered it then gets populated into DOCVARIABLES within the document. But if I run the code again (when the DOCVARIABLES are storing the data already) it gives me an error: Run-Time Error "5903": The Variable name already exists.
The question is how to fix it and make the DOCVARIABLES updatable.
Here is a solution Cindy Meister provided, but with introduction of array:
Sub Document_Open()
Dim sNumber As String, mNumber As String, iDate As String, i As Integer
Dim varData(1 To 3) As String
varData(1) = "SerialNumber"
varData(2) = "ModelNumber"
varData(3) = "IssueDate"
Dim varInput(1 To 3) As String
varInput(1) = InputBox("Please enter the Serial Number", "Serial number", "Enter the Serial Number here")
varInput(2) = InputBox("Please enter the Model Number", "Model number", "Enter the Model Number here")
varInput(3) = InputBox("Please enter the Date of Issue, dd.mm.yyyy", "Date of Issue", "Enter the Date of Issue here")
For i = 1 To 3
With ActiveDocument
If DocVarExists(varData(i), ActiveDocument) Then
.Variables(varData(i)).Value = varInput(i)
Else
.Variables.Add Name:=varData(i), Value:=varInput(i)
End If
.Fields.Update
End With
Next i
End Sub
Function DocVarExists(sVarName As String, doc As Word.Document) As Boolean
Dim var As Word.Variable, bExists As Boolean
bExists = False
For Each var In doc.Variables
If var.Name = sVarName Then
bExists = True
Exit For
End If
Next
DocVarExists = bExists
End Function
With document Variables
you have two possibilities.
The "simple" one is to simply assign the value. There's no need to use the Add
method at all. So you need only one line of code, whether the Variable
already exists in the document or not:
ActiveDocument.Variables("name").Value = "new value"
(Note: Variables
originate from the old, Word Basic days, where things were much less formal than they've become. A CustomDocumentProperty
, in contrast, requires an Add
method - the object was introduced in the VBA days.)
If you want things to be very correct, then you'd need to loop through the Variables
collection to find out if it already exists and only add it if it does. I have a little function for this which I've pasted below and put a call to it in your code. (Which I've edited for only one Variable
to make it easier to follow the function call.)
Sub Document_Open()
Dim sNumber as String, mNumber As String, iDate As String
sNumber = InputBox("Please enter the Serial Number", "Serial number", _
"Enter the Serial Number here")
With ActiveDocument
If DocVarExists("SerialNumber", ActiveDocument) Then
.Variables("SerialNumber").Value = sNumber
Else
.Variables.Add Name:="SerialNumber", Value:=sNumber
End If
.Fields.Update
End With
End Sub
Function DocVarExists(sVarName As String, doc As Word.Document) As Boolean
Dim var As Word.Variable, bExists As Boolean
bExists = False
For Each var In doc.Variables
If var.Name = sVarName Then
bExists = True
Exit For
End If
Next
DocVarExists = bExists
End Function
(Note: This is the approach required for CustomDocumentProperties
.)
Just a remark about Variable
objects for anyone reading this that's not familiar with them: As soon as an emtpy (zero-length) string is assigned the Variable
object is deleted and no longer available in the document.