Search code examples
vbapowerpointpowerpoint-2007

Find and Highlight Text in MS PowerPoint


I used some code from this site to make a macro to do a keyword search on Word docs and highlight the results.

I would like to replicate the effect in PowerPoint.

Here is my code for Word.

Sub HighlightKeywords()

Dim range As range
Dim i As Long
Dim TargetList

TargetList = Array("keyword", "second", "third", "etc") ' array of terms to search for

For i = 0 To UBound(TargetList) ' for the length of the array

   Set range = ActiveDocument.range

   With range.Find ' find text withing the range "active document"
   .Text = TargetList(i) ' that has the words from the array TargetList
   .Format = True ' with the same format
   .MatchCase = False ' and is case insensitive
   .MatchWholeWord = True ' and is not part of a larger word
   .MatchAllWordForms = False ' and DO NOT search for all permutations of the word

   Do While .Execute(Forward:=True)
   range.HighlightColorIndex = wdYellow ' highlight the keywords from the for loop yellow

   Loop

   End With
Next

End Sub

Here is what I have so far in PowerPoint, it is in no way functional.

Sub HighlightKeywords()

Dim range As range
Dim i As Long
Dim TargetList

TargetList = Array("keyword", "second", "third", "etc") ' array of terms to search for

For Each sld In Application.ActivePresentation.Slides

For Each shp In sld.Shapes

    If shp.HasTextFrame Then

        Set txtRng = shp.TextFrame.TextRange

For i = 0 To UBound(TargetList) ' for the length of the array

   With range.txtRng ' find text withing the range "shape, text frame, text range"
   .Text = TargetList(i) ' that has the words from the array TargetList
   .Format = True ' with the same format
   .MatchCase = False ' and is case insensitive
   .MatchWholeWord = True ' and is not part of a larger word
   .MatchAllWordForms = False ' and DO NOT search for all permutations of the word

   Do While .Execute(Forward:=True)
   range.HighlightColorIndex = wdYellow ' highlight the keywords from the for loop yellow

   Loop

   End With
Next

End Sub

I ended up finding my answer through the MSDN, but it was very close to the answer I selected as correct from what people submitted.

Here is the code I went with:

Sub Keywords()

Dim TargetList
Dim element As Variant

TargetList = Array("First", "Second", "Third", "Etc")

For Each element In TargetList
   For Each sld In Application.ActivePresentation.Slides
      For Each shp In sld.Shapes
         If shp.HasTextFrame Then
            Set txtRng = shp.TextFrame.TextRange
            Set foundText = txtRng.Find(FindWhat:=element, MatchCase:=False, WholeWords:=True)
            Do While Not (foundText Is Nothing)
               With foundText
                  .Font.Bold = True
                  .Font.Color.RGB = RGB(255, 0, 0)
               End With
            Loop
         End If
      Next
   Next
Next element

End Sub

Turns out that code worked, but was a performance nightmare. The code I selected as the correct answer below runs much more smoothly. I've adjusted my program to match the answer selected.


Solution

  • AFAIK there is no inbuilt way to highlight the found word with a color. You could go out of the way to create a rectangular shape and place it behind the found text and color it but that is a different ball game altogether.

    Here is an example which will search for the text in all slides and then make the found text BOLD, UNDERLINE and ITALICIZED. If you want you can also change the color of the font.

    Let's say we have a slide which looks like this

    enter image description here

    Paste this code in a module and then try it. I have commented the code so that you will not have a problem understanding it.

    Option Explicit
    
    Sub HighlightKeywords()
        Dim sld As Slide
        Dim shp As Shape
        Dim txtRng As TextRange, rngFound As TextRange
        Dim i As Long, n As Long
        Dim TargetList
    
        '~~>  Array of terms to search for
        TargetList = Array("keyword", "second", "third", "etc")
    
        '~~> Loop through each slide
        For Each sld In Application.ActivePresentation.Slides
            '~~> Loop through each shape
            For Each shp In sld.Shapes
                '~~> Check if it has text
                If shp.HasTextFrame Then
                    Set txtRng = shp.TextFrame.TextRange
    
                    For i = 0 To UBound(TargetList)
                        '~~> Find the text
                        Set rngFound = txtRng.Find(TargetList(i))
    
                        '~~~> If found
                        Do While Not rngFound Is Nothing
                            '~~> Set the marker so that the next find starts from here
                            n = rngFound.Start + 1
                            '~~> Chnage attributes
                            With rngFound.Font
                                .Bold = msoTrue
                                .Underline = msoTrue
                                .Italic = msoTrue
                                '~~> Find Next instance
                                Set rngFound = txtRng.Find(TargetList(i), n)
                            End With
                        Loop
                    Next
                End If
            Next
        Next
    End Sub
    

    Final Screenshot

    enter image description here