The final example in this trilogy of replacements using lists was prompted by a newsgroup question. The user wanted initially to highlight words and phrases in a document from a list, which was easily achieved using a variation of one of the above macros, and the he ventured the possibility of the user choosing from a number of possible replacements. How practical this is in a real life situation I cannot say, but the principles involved I felt were interesting enough to repeat them here.
In this instance the macro uses a multi-column table. The first column contains the words to be located, the subsequent columns contain the replacement choices. The columns should be filled from left to right. Not all the columns (except the first) need contain any data, but the columns must be filled from left to right with no gaps.
If only the second column has data, the found item is replaced with the content of the second column
If more columns to the right of the second column have data, the choices from the second and subsequent columns are presented as numbered choices in a list.
If none of the columns, except the first, contains data, then the found word is merely highlighted.
There must be no empty cells in the first column!
Sub ReplaceFromTableChoices()
Dim ChangeDoc, RefDoc As Document
Dim cTable As Table
Dim oldPart, newPart, oFound As Range
Dim i, j, iCol As Long
Dim sFname, sReplaceText, sNum As String
'Define the document containing the table of changes.
Dim ChangeDoc, RefDoc As Document
Dim cTable As Table
Dim oldPart, newPart, oFound As Range
Dim i, j, iCol As Long
Dim sFname, sReplaceText, sNum As String
'Define the document containing the table of changes.
'The table must have at least 3 columns.
sFname = "D:\My Documents\Test\changes2.doc"
sFname = "D:\My Documents\Test\changes2.doc"
'Define the document to be processed
Set RefDoc = ActiveDocument
Set ChangeDoc = Documents.Open(sFname)
Set RefDoc = ActiveDocument
Set ChangeDoc = Documents.Open(sFname)
'Define the table to be used
Set cTable = ChangeDoc.Tables(1)
Set cTable = ChangeDoc.Tables(1)
'Activate the document to be processed
RefDoc.Activate
RefDoc.Activate
'Process each row of the table in turn
For i = 1 To cTable.Rows.Count
'Set the search item to the content of the first cell
Set oldPart = cTable.Cell(i, 1).Range
Set oldPart = cTable.Cell(i, 1).Range
'Remove the cell end character from the range
oldPart.End = oldPart.End - 1
oldPart.End = oldPart.End - 1
'Start from the beginning of the document
With Selection
.HomeKey wdStory
With .Find
.ClearFormatting
.Replacement.ClearFormatting
.MatchWholeWord = True
.MatchCase = True
With Selection
.HomeKey wdStory
With .Find
.ClearFormatting
.Replacement.ClearFormatting
.MatchWholeWord = True
.MatchCase = True
'Look for the search item
Do While .Execute(findText:=oldPart)
Do While .Execute(findText:=oldPart)
'And assign the found item to a range variable
Set oFound = Selection.Range
Set oFound = Selection.Range
'Set the start number of a counter
iCol = 1
iCol = 1
'Set a temporary replacement text string to zero length
sReplaceText = ""
sReplaceText = ""
'Look into the remaining columns for replacement choices
For j = 2 To cTable.Columns.Count
For j = 2 To cTable.Columns.Count
'And assign the replacement choices to a range variable in turn
Set newPart = cTable.Cell(i, j).Range
Set newPart = cTable.Cell(i, j).Range
'Remove the cell end character from the range
newPart.End = newPart.End - 1
newPart.End = newPart.End - 1
'If the current cell has no content, ignore the remainder
If Len(newPart) = 0 Then Exit For
If Len(newPart) = 0 Then Exit For
'Add the range content to the temporary replacement text string
sReplaceText = sReplaceText & iCol & ". " & _
newPart.Text & vbCr
sReplaceText = sReplaceText & iCol & ". " & _
newPart.Text & vbCr
'Increment the counter
iCol = iCol + 1
Next j
iCol = iCol + 1
Next j
'If there is a replacement available
If Len(sReplaceText) <> 0 Then
If Len(sReplaceText) <> 0 Then
'If there is only one such replacement
If Len(cTable.Cell(i, 2).Range) <> 2 And _
Len(cTable.Cell(i, 3).Range) = 2 Then
'Set the number of that replacement to 1
If Len(cTable.Cell(i, 2).Range) <> 2 And _
Len(cTable.Cell(i, 3).Range) = 2 Then
'Set the number of that replacement to 1
sNum = "1"
Else
Again: 'Add a label to mark the start of the user input
Else
Again: 'Add a label to mark the start of the user input
'If there is more than one choice,
'ask the user to pick the preferred replacement
sNum = InputBox(sReplaceText & vbCr & vbCr & _
"Enter the number of the replacement for '" _
& oldPart.Text & "'")
If sNum = "" Then Exit Sub 'The user has cancelled
sNum = InputBox(sReplaceText & vbCr & vbCr & _
"Enter the number of the replacement for '" _
& oldPart.Text & "'")
If sNum = "" Then Exit Sub 'The user has cancelled
'Error trap inappropriate user choices
'Check if the user has entered something other than a number
If IsNumeric(sNum) = False Then
If IsNumeric(sNum) = False Then
'Tell the user
MsgBox "Invalid entry! Try again.", _
vbInformation, "Error"
MsgBox "Invalid entry! Try again.", _
vbInformation, "Error"
'and go round again
GoTo Again
End If
GoTo Again
End If
'Check if the user has entered a number
'higher than the number of columns in the table
If sNum > cTable.Columns.Count Then
If sNum > cTable.Columns.Count Then
'Tell the user
MsgBox "Invalid entry! Try again.", _
vbInformation, "Error"
MsgBox "Invalid entry! Try again.", _
vbInformation, "Error"
'and go round again
GoTo Again
End If
GoTo Again
End If
'Check if a user has picked a valid number
'higher than the available choices
If Len(cTable.Cell(i, sNum + 1).Range) = 2 Then
'Tell the user
If Len(cTable.Cell(i, sNum + 1).Range) = 2 Then
'Tell the user
MsgBox "Invalid entry! Try again.", _
vbInformation, "Error"
vbInformation, "Error"
'and go round again
GoTo Again
End If
End If
GoTo Again
End If
End If
'Set the replacement according to the user input
Set newPart = cTable.Cell(i, sNum + 1).Range
newPart.End = newPart.End - 1
oFound.Text = newPart.Text
Else
Set newPart = cTable.Cell(i, sNum + 1).Range
newPart.End = newPart.End - 1
oFound.Text = newPart.Text
Else
'There are no replacements so highlight the found item
oFound.HighlightColorIndex = wdYellow
End If
Loop
End With
End With
Next i
oFound.HighlightColorIndex = wdYellow
End If
Loop
End With
End With
Next i
'Close the document containing the table
ChangeDoc.Close wdDoNotSaveChanges
End Sub
ChangeDoc.Close wdDoNotSaveChanges
End Sub
No comments:
Post a Comment