I have a document in Word which contains hundreds of the Italicized words that have no space in between themselves and the previous word.
For example:
The quickbrown fox jumps over the lazydog.
The result I am looking for is:
The quick brown fox jumps over the lazy dog.
I've been trying to construct a macro using the Find and replace and .InsertBefore to solve this issue for me but with no success.
This is the code I have so far.
Sub FindItalics()
Selection.Find.ClearFormatting
Selection.Find.Font.Italic = True
With Selection.Find
.Text = ""
.Replacement.Text = ""
.Forward = True
.Wrap = wdFindContinue
.Format = True
.MatchCase = False
.MatchWholeWord = False
.MatchWildcards = False
.MatchSoundsLike = False
.MatchAllWordForms = False
End With
Selection.Find.Execute
InsertBefore
End Sub
Sub InsertBefore()
With Selection
.InsertBefore " "
End With
End Sub
I have found that this works and does what I require, however it only does it for the first italicized word in the document and will not continue throughout the rest of the document.
I think you can do this without VBA:
In Word's Find/Replace turn on search with wildcards, search for Format, Font..., Italic and search for the pattern (*>).
The * means find anything,
the > means find to the end of the word, and
the () parentheses will create a autonumbered group when the pattern is matched.
In the Replace box, don't change the format and Replace with text: <space>\1 to insert a space followed by group #1.
This worked for me:
Sub FindItalics()
Dim rng As Range
Set rng = Selection.Range
With rng.Find
.Text = ""
.Replacement.Text = ""
.ClearFormatting
.Wrap = wdFindStop
.Format = True
.Font.Italic = True
.MatchWholeWord = False
.Forward = True
While .Execute
'Note: 'rng' is now the range containing the matched content
rng.InsertBefore " "
rng.Collapse wdCollapseEnd
Wend
End With
End Sub
Related
I am trying to create a Word macro that will:
Search for a specific word (i.e. "see")
Select the entire paragraph where that word appears
Make the whole paragraph a different style (i.e. make it all red text)
Do the same thing with a second word (i.e. "blacklist")
Select that whole paragraph and apply a different style (i.e. again, make the paragraph red text)
Copy all paragraphs with the red text style and paste them in to a new word document
Unfortunately, I'm no VBA expert and I'm trying to cobble things together from what I can find online. I have found a great example that will select to the start of the paragraph, but I can't seem to figure out how to select the entire paragraph. Any help is appreciated!
** Sorry - here is the code I currently have. It will find all instances of the word "see" and selects to the start of the paragraph, then changes the color to red... but that's as far as I've gotten, as I am stuck on trying to figure out how to get it to select to the end of the paragraph.
Sub TestOne()
'
' TestOne Macro
'
'
If MsgBox(Prompt:="Would you like to update selected paragraph styles?", Buttons:=vbYesNo + vbQuestion, _
Title:="Format MD Report") = vbNo Then
Exit Sub
End If
Application.ScreenUpdating = False
Dim i As Long
With ActiveDocument.Range
With .Find
.ClearFormatting
.Replacement.ClearFormatting
.Text = "see"
.Replacement.Text = ""
.Forward = True
.Wrap = wdFindStop
.Format = False
.MatchWildcards = False
End With
Do While .Find.Execute
i = i + 1
.Start = .Paragraphs.First.Range.Start
.Font.Color = wdColorRed
.Start = .Paragraphs.First.Range.End
Loop
End With
Application.ScreenUpdating = True
MsgBox i & " instances processed."
End Sub
For example, without needing to create a second document:
Sub Demo()
Application.ScreenUpdating = False
Dim i As Long, StrFnd As String
StrFnd = "see|blacklist"
With ActiveDocument.Range
.Font.Hidden = True
With .Find
.ClearFormatting
.Replacement.ClearFormatting
.Replacement.Text = "^&"
.Font.Hidden = True
.Replacement.Font.Hidden = False
.Format = True
.Forward = True
.MatchWildcards = True
.Wrap = wdFindContinue
For i = 0 To UBound(Split(StrFnd, "|"))
.Text = "[!^13]#" & Split(StrFnd, "|")(i) & "*^13"
.Execute Replace:=wdReplaceAll
Next
.Replacement.ClearFormatting
.Text = ""
.Replacement.Text = ""
.Execute Replace:=wdReplaceAll
End With
End With
Application.ScreenUpdating = True
End Sub
You could, of course, add a line of code before the final 'End With' to save the document with a new name.
To select the entire paragraph, following the line
.Start = .Paragraphs.First.Range.Start
add
.End = .Paragraphs.First.Range.End
... then to match only whole words, after
.MatchWildcards = False
add
.MatchWholeWord = True
And to run the code for multiple words you should add a parameter to your Sub eg
Sub TestOne(theWord As String)
then replace
.Text = "see"
with
.Text = theWord
And to run your code for each required word, add a Sub such as
Sub RunMe()
TestOne "see"
TestOne "blacklist"
End Sub
... optionally, move your MsgBoxes into RunMe()
I am using Word VBA. I want to find a specific keyword "MyTest" from the beginning of the document, and then repeat until all of occurrences are found. How to do so?
I use macro record, and get the following codes:
Selection.Find.ClearFormatting
With Selection.Find
.Text = "MyTest"
.Replacement.Text = ""
.Forward = True
.Wrap = wdFindContinue
.Format = False
.MatchCase = False
.MatchWholeWord = False
.MatchByte = False
.MatchWildcards = False
.MatchSoundsLike = False
.MatchAllWordForms = False
End With
Selection.Find.Execute
This seems only start the find from the current position and will return one instance of the keyword?
The macro recorder will not give you the best code as it can only record what you do on screen. This means that it always works with the Selection object, i.e. whatever you have selected on screen.
Instead you should use a Range object set to the the part of the document you want to work with. Unless you are using ReplaceAll you also need to repeatedly execute the Find until you have found all the matches.
Below is a generic routine that you can modify.
Sub FindSomeTextAndDoSomething(textToFind As String)
Dim findRange As Range
Set findRange = ActiveDocument.Content
With findRange.Find
.ClearFormatting
.Text = textToFind
.Replacement.Text = ""
.Wrap = wdFindStop
.Format = False
Do While .Execute = True
'add code here to do something with the found text
'collapse range to continue
findRange.Collapse wdCollapseEnd
Loop
End With
End Sub
I am not familiar with VBA at all.
I want to search for text I select (rather than a given list of words or typing that text in a box), and then change its format (preferably make it bold or change its color).
I tried to change a few macros that I found.
The VBA code for this can be rather simple. For example:
Sub MakeBold()
Application.ScreenUpdating = False
With ActiveDocument.Range
With .Find
.ClearFormatting
.Replacement.ClearFormatting
.Replacement.Font.Bold = True
.Text = Selection.Text
.Replacement.Text = "^&"
.Forward = True
.Wrap = wdFindContinue
.Format = True
.Execute Replace:=wdReplaceAll
End With
End With
Application.ScreenUpdating = True
End Sub
For PC macro installation & usage instructions, see: http://www.gmayor.com/installing_macro.htm
For Mac macro installation & usage instructions, see: https://wordmvp.com/Mac/InstallMacro.html
This will do what you want. Copy/paste into your VB editor window.
Sub HighlightWords()
Dim Word As Range
Dim WordCollection(2) As String
Dim Words As Variant
'Define list.
'If you add or delete, change value above in Dim statement.
WordCollection(0) = "you"
WordCollection(1) = "or"
WordCollection(2) = "Word document"
'Set highlight color.
Options.DefaultHighlightColorIndex = wdYellow
'Clear existing formatting and settings in Find feature.
Selection.Find.ClearFormatting
Selection.Find.Replacement.ClearFormatting
'Set highlight to replace setting.
Selection.Find.Replacement.Highlight = True
'Cycle through document and find words in collection.
'Highlight words when found.
For Each Word In ActiveDocument.Words
For Each Words In WordCollection
With Selection.Find
.Text = Words
.Replacement.Text = ""
.Forward = True
.Wrap = wdFindContinue
.Format = True
.MatchCase = False
.MatchWholeWord = False
.MatchWildcards = False
.MatchSoundsLike = False
.MatchAllWordForms = False
End With
Selection.Find.Execute Replace:=wdReplaceAll
Next
Next
End Sub
Before:
After:
I have a Find and Replace macro that adds a space between the end of one sentence and the beginning of another when missing. This sometimes happens when I move sentences around in word.
I notice that if the cursor is to either side of the punctuation mark, the macro can’t see the Find pattern and doesn’t fix it. I assume it’s because Find and Replace starts searching from the cursor position. Is there a way to tweak the code so it finds them too?
I know I could just tell the macro to start from the beginning, but I would much rather it left the cursor in its current position, especially if I run it near the end of a long document.
Sub AddOneSpaceBetweenSentences()
' AddOneSpaceBetweenSentences Macro
'
With Selection.Find
.Forward = True
.Text = "(?)([.\?\!])([A-Z])"
.ClearFormatting
.Replacement.Text = "\1\2 \3" 'there is a space between \2 and \3
.MatchWildcards = True
.Wrap = wdFindContinue
.Execute Replace:=wdReplaceAll
End With
End Sub
Better still:
Sub AddOneSpaceBetweenSentences()
Application.ScreenUpdating = False
With ActiveDocument.Range.Find
.ClearFormatting
.Replacement.ClearFormatting
.Forward = True
.Format = False
.MatchWildcards = True
.Wrap = wdFindContinue
.Text = "([.\?\!])([A-Z])"
.Replacement.Text = "\1 \2"
.Execute Replace:=wdReplaceAll
End With
Application.ScreenUpdating = True
End Sub
The most reliable way is to use Range objects instead of Selection. When working with a Range the selection in the document doesn't change.
Sub AddOneSpaceBetweenSentences()
' AddOneSpaceBetweenSentences Macro
'
Dim rng as Word.Range
Set rng = ActiveDocument.Content
With rng.Find
.Forward = True
.Text = "(?)([.\?\!])([A-Z])"
.ClearFormatting
.Replacement.Text = "\1\2 \3" 'there is a space between \2 and \3
.MatchWildcards = True
.Wrap = wdFindContinue
.Execute Replace:=wdReplaceAll
End With
End Sub
Is it really necessary to have a character before the end signs . or ? or !
If not, just replace "([.\?\!])([A-Z])" by "\1 \2"
Simple attempt: Just extend the selection by 2 characters to the left.
If cursor is on the first two characters of the documents, you would get an error. To prevent that and to prevent counting of characters, I just used Selection.Start > 10
If Selection.Start > 10 Then
Selection.Previous(Unit:=wdCharacter, Count:=2).Select
End If
... or do it a little more complicated:
Sub AddOneSpaceBetweenSentences()
Dim SearchText As String
Dim ReplaceText As String
' extend selection by 1 character
If Selection.Start > 0 Then
Selection.Previous(Unit:=wdCharacter, Count:=1).Select
End If
Selection.Collapse
' if selection begins directly before end of sentence (.?!)
' adapt search & replace pattern
If InStr(1, ".?!", Selection.Characters(1), vbBinaryCompare) > 0 Then
SearchText = "([.\?\!])([A-Z])"
ReplaceText = "\1 \2"
Else
SearchText = "(?)([.\?\!])([A-Z])"
ReplaceText = "\1\2 \3"
End If
With Selection.Find
.Forward = True
.text = SearchText
.ClearFormatting
.Replacement.text = ReplaceText
.MatchWildcards = True
.Wrap = wdFindContinue
.Execute Replace:=wdReplaceAll
End With
End Sub
I have a Word table where I apply a routine that replaces paragraph marks with a comma and a space. However, in doing so there is now some text like '..., There...' and my client wanted to replace the Upper Case to Lower Case as much as possible.
So, I wrote some secondary code that I call from the previous routine as follows:
Sub LowerCaseAfterComma()
With Selection.Find
.ClearFormatting
.Text = ", ([A-Z])"
.Forward = True
.Wrap = wdFindStop
.Format = True
.MatchCase = False
.MatchWholeWord = False
.MatchWildcards = True
.MatchSoundsLike = False
.MatchAllWordForms = False
.Execute
While .Found
Selection.Range.Case = wdLowerCase
Selection.Collapse Direction:=wdCollapseEnd
.Execute
Wend
End With
End Sub
Although this identifies the instances of Upper Case characters in the table and replaces them accordingly, the code then looks for all other instances outside the table in the document, which I don't want the code to do. I have tried using the Range object in Word for the table I want edited but haven't been successful in the syntax needed.
NB. I have problems in ensuring the editing stays within the specific table. There can be a differing number of tables prior to the one I wish to edit so
ActiveDocument.Tables() specifying the number of the table doesn't seem to work.
I am sure I doing some basically wrong and the code just needs a little tinkering. However, I am just a novice developer learning.
Try
Sub Demo()
Application.ScreenUpdating = False
Dim Rng As Range
With ActiveDocument.Tables(1)
Set Rng = .Range
With .Range
With .Find
.ClearFormatting
.Replacement.ClearFormatting
.Text = ", ([A-Z])"
.Replacement.Text = ""
.Forward = True
.Wrap = wdFindStop
.Format = False
.MatchWildcards = True
.Execute
End With
Do While .Find.Found
If .InRange(Rng) Then
.Case = wdLowerCase
Else
Exit Do
End If
.Collapse wdCollapseEnd
.Find.Execute
Loop
End With
End With
Application.ScreenUpdating = True
End Sub