Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Chris Miller on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

using Find in a vba macro 2

Status
Not open for further replies.

programmerinthedark

Programmer
Nov 19, 2010
11
GB
Hello, I hope someone out there can help, as this particular problem is driving me mad. I've been asked to write a customized index builder for ms word 2003. The words I'm having to look for are contained in an array, and I use the Find command to look through the document. All was fine, until I discovered that footnotes, comments, endnotes etc had not been included in my search. Having messed about with this for a while, I think it may be something to do with Ranges, and that I may need to search each range within the document. The odd thing is that if you do a find manually in word 2003, all ranges are searched. I'd be deeply indebted to anyone who can help with tis one.
 
Straight from the VBA help:
Code:
For Each myStoryRange In ActiveDocument.StoryRanges
    myStoryRange.Find.Execute  _
        FindText:="Microsoft Word", Forward:=True
    While myStoryRange.Find.Found
        myStoryRange.Italic = True
        myStoryRange.Find.Execute  _
            FindText:="Microsoft Word", Forward:=True
    Wend
    While Not (myStoryRange.NextStoryRange Is Nothing)
        Set myStoryRange = myStoryRange.NextStoryRange
        myStoryRange.Find.Execute  _
            FindText:="Microsoft Word", Forward:=True
        While myStoryRange.Find.Found
            myStoryRange.Italic = True
            myStoryRange.Find.Execute  _
                FindText:="Microsoft Word", Forward:=True
        Wend
    Wend
Next myStoryRange

Hope This Helps, PH.
FAQ219-2884
FAQ181-2886
 
Thanks very much for this very helpful post. It has opened a tiny door in my memory, and I'm in the process of implementing (with some small changes) the offered code.
 
Hi again,
At the risk of becoming boring, there seems to be a problem with the way I'm referring to things in this macro.
Consider the following:
set myrange=activedocument.storyranges(wdmaintextstory)
Do While blnFound = True
myRange.Find.ClearFormatting
With myRange.Find
.Text = strFindText
.Replacement.Text = ""
.Forward = True
.Wrap = wdFindStop
.Format = False
.MatchCase = False
.MatchWholeWord = False
.MatchWildcards = True
.MatchSoundsLike = False
.MatchAllWordForms = False
End With
If myRange.Find.Execute Then
Selection.MoveRight Unit:=wdCharacter, Count:=7, Extend:=wdExtend
intPageNo = Selection.Information(wdActiveEndPageNumber)
strFoundText = Selection.Text
Given that there is an end if etc, this code returns the first few characters in the document, and not the expected string. I have debugged it, and it is finding the string, but not placing it in a variable.
Help!!
Best PID
 
Hi PID,

Try the following:
Code:
Sub Demo()
Dim myRng As Range, fRng As Range, intPageNo As Integer
Dim strFindTxt As String, strFoundTxt As String
'Application.ScreenUpdating = False
strFindTxt = InputBox("What is the string to Find?")
Set myRng = Selection.Range
ActiveDocument.StoryRanges(wdMainTextStory).Select
With Selection.Find
   .ClearFormatting
   .Text = strFindTxt
   .Replacement.Text = ""
   .Forward = True
   .Wrap = wdFindStop
   .Format = False
   .MatchCase = False
   .MatchWholeWord = False
   .MatchWildcards = True
   .MatchSoundsLike = False
   .MatchAllWordForms = False
   .Execute
   Do While .Execute = True
        Set fRng = ActiveDocument.Range(Start:=Selection.Start, End:=Selection.End)
        With fRng
             .End = .End + 7
             intPageNo = .Information(wdActiveEndPageNumber)
             strFoundTxt = .Text
        End With
        MsgBox intPageNo & " " & strFoundTxt
    Loop
End With
myRng.Select
Set fRng = Nothing: Set myRng = Nothing
Application.ScreenUpdating = True
End Sub
Once you're happy that it's working as desired, un-comment the 'Application.ScreenUpdating = False' line, replace the message box with whatever other process you want to run.


Cheers
[MS MVP - Word]
 
Thanks MP,
I throw my hands up in horror. Various bits there I should have known, and I've stored your code in my snippets folder.
Best PID.
 
Hi again Macropod et al,
Everything works fine now but...
The macro searches the main document with no problem, but I've got a loop so that once it has searched the main document, the selection is set to the Footnotes range. Having inserted this code, it gets into a loop. Having stuck some Msgbox code in, it looks like it is getting stuck on the first instance of a string in the footnotes. Does this range contain many footnote objects, in other words, do I have to set up a different process to search the footnotes. I hope not.

Best PID.
 
Hi PID,

It would be helpful if you posted the code you're using.


Cheers
[MS MVP - Word]
 
Hi Macropod,
Here is the code:
For intRangeSelect = 1 To 2
If intRangeSelect = 1 Then
ActiveDocument.StoryRanges(wdMainTextStory).Select
Else
ActiveDocument.StoryRanges(wdFootnotesStory).Select
End If
With Selection.Find
.ClearFormatting
.Text = strFindText
.Replacement.Text = ""
.Forward = True
.Wrap = wdFindStop
.Format = False
.MatchCase = False
.MatchWholeWord = False
.MatchWildcards = True
.MatchSoundsLike = False
.MatchAllWordForms = False
.Execute
Do While .Execute = True
Set fRange = ActiveDocument.Range(Start:=Selection.Start, End:=Selection.End)
With fRange
.End = .End + 7
intPageNo = .Information(wdActiveEndPageNumber)
strFoundText = .Text
End With
'processing found string goes here
Loop
End With
Next intRangeSelect
the intRangeSelect variable determines which range should be used, and the text I'm looking for will either be in the main document or the footnotes.
Thanks, PID.
 
You should be using the range of the footnotes story, NOT selecting it.


unknown
 
Hi PID,

First off, please use code tags when posting code.

To process all possible text ranges, try the following:
Code:
Sub Demo()
Dim myRng As Range, fRng As Range, intPageNo As Integer
Dim strFindTxt As String, strFoundTxt As String, strStory As String
Application.ScreenUpdating = False
strFindTxt = InputBox("What is the string to Find?")
For Each myRng In ActiveDocument.StoryRanges
    Set fRng = myRng
    With myRng.Find
        .ClearFormatting
        .Text = strFindTxt
        .Replacement.Text = ""
        .Forward = True
        .Wrap = wdFindStop
        .Format = False
        .MatchCase = True
        .MatchWholeWord = False
        .MatchWildcards = True
        .MatchSoundsLike = False
        .MatchAllWordForms = False
        Do While .Execute
            With fRng
              'processing found strings occurs here
              .Start = .Start + InStr(.Text, strFindTxt) - 1
              .End = .Start + Len(strFindTxt) + 7
              intPageNo = .Information(wdActiveEndPageNumber)
              strFoundTxt = .Text
              strStory = .StoryType
              .Collapse (wdCollapseEnd)
            End With
            'processing string variables goes here
            MsgBox intPageNo & vbCr & strFoundTxt & vbCr & strStory
        Loop
    End With
Next myRng
Set fRng = Nothing: Set myRng = Nothing
Application.ScreenUpdating = True
End Sub
Note: When processing headers and footers, you're liable to get more 'hits' than you expect, due to the way these are handled (with 3 of each per Section, each of which except the first can be linked to the previous Section). Of course, it you're not interested in processing headers and footers, you can add a test for the StoryType before starting the 'Find' process.


Cheers
[MS MVP - Word]
 
Hi Macropod,
I apologize for not using code tags. I'm blind (hence the handle), and didn't spot the "Code" tag there. Now I'm aware of it, I'll use it. As to the code, I'll probably use an if statement so that only footnotes and maintext are processed. About to try it.
Best, PID.
 
Hi PID,

After making my last post above I realised that, since you're using wildcards, the solution I posted wo't work. Accordingly, try the following:
Code:
Sub Demo()
Application.ScreenUpdating = False
Dim RngStory As Range, IntPageNo As Integer
Dim StrFindTxt As String, StrFoundTxt As String
StrFindTxt = InputBox("What is the string to Find?")
If Trim(StrFindTxt) = "" Then Exit Sub
For Each RngStory In ActiveDocument.StoryRanges
  With RngStory
    If .StoryType = wdMainTextStory _
      Or .StoryType = wdFootnotesStory Then
        With .Find
          .ClearFormatting
          .Text = StrFindTxt
          .Replacement.Text = ""
          .Forward = True
          .Wrap = wdFindStop
          .Format = False
          .MatchCase = False
          .MatchWholeWord = False
          .MatchWildcards = True
          .MatchSoundsLike = False
          .MatchAllWordForms = False
          Do While .Execute
            With RngStory.Duplicate
              'process the found strings
              .End = .End + 7
              IntPageNo = .Information(wdActiveEndPageNumber)
              StrFoundTxt = .Text
              'do stuff here
              MsgBox IntPageNo & vbCr & StrFoundTxt
              .Collapse (wdCollapseEnd)
            End With
          Loop
        End With
    End If
  End With
Next RngStory
Application.ScreenUpdating = True
End Sub


Cheers
[MS MVP - Word]
 
Hi Macropod,
Yes, this code works, and the only thing I had to change was the .end setting. I needed 7 characters after the string, so that I could pick up some stuff after it, if it existed. However, this causes a slight problem if you have two matching strings which may be on the same line, and the extra 7 characters you've grabbed happen to be the start of the next string you want to find. This is solved by resetting .end once you've grabbed strfoundtxt. Tricky to explain this in writing, but I guess you can see what I mean. All sorted now anyway, thanks for help
Best PID.
 
Hi PID,

To do that, you could simply insert:
.End = .End - 7
before:
.Collapse (wdCollapseEnd)

I assume you did something along those lines.


Cheers
[MS MVP - Word]
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top