View Full Version : Final hurdle for combined comment and revision grid
h2whoa
06-28-2018, 08:25 AM
So, many of the dumb questions that I've been asking recently are because I've been working on trying to update the famous comment and revision trackers by Lene Fredborg, DocTools. I claim no particular credit for any of the code below. Most of it is just modified from the Lene Fredborg original. I'm also indebted to macropod, gmayor and John Wilson for their extreme helpfulness while I've been trying to get to grips with VBA. All of this is to say: I am not attempting to steal any credit for other's hard work.
However, I have hit a final brick wall that I am wasting a lot of time trying to get past and so I'm crying out for one last bit of help on this.
The modified code is now a combined revision and comment grid maker, with options to do one or the other (or both). It also gives you the option to exclude comments and revisions from specific authors.
But I'm having a problem that I can't seem to get around at the last part. For some reason, I can no longer populate the final table with the details of the tracked insertions and deletions. It is still counting them, and creating the right number of rows, but it is not populating the cells with the information for each revision. Obviously that's a problem!
When you look at the code, you may wonder why I've gone for cycling through revisions using "For integer = 1 to revision counts" loops, instead of using the neater "For Each Revision in ActiveDocument.Revisions". I've found that using the neater method creates a runtime error if there are overlapping revisions, in which VBA seems to fall over in trying to define the Revision.Type.
So I used the messier 'For 1 to...' method to get around this. I know this seems to work in the other instances of the code, as it is producing an accurate list of revision authors and number of insertions and deletions. But it seems to be failing at the last bit of the macro (in the "Tracks:" section), so I end up with a blank table. If anyone can work out why it is doing this, and how I can get around it, while still avoiding the runtime error that comes from "For Each Revision...", you'll have made my week. Maybe my year.
Public Sub Rev_and_Comm_Tracker()
    Dim oDoc, oNewDoc As Document
    Dim oTable As Table
    Dim oRange As Range
    Dim nCount, n, i, numRows, rCount, rCount2, rTb, cTb, blRows, cax, rax, b, c, d, j, k, w, x, y, z, cmCounter, revCounter, sCmtTally, sRevTally As Long
    Dim noCol As Integer
    Dim Title, strText, selType, selType2, finSel, exAuth, exRev, exAuthNum, exRevNum, Auth2ex1, Auth2ex2, Auth2ex3, Auth2ex4, Auth2ex5 As String
    Dim Rev2ex1, Rev2ex2, Rev2ex3, Rev2ex4, Rev2ex5, initCSum, initRSum As String
    Dim sCmAuTxt1, sCmAuTxt2, sCmAuTxt3, sCmAuTxt4, sRvAuTxt1, sRvAuTxt2, sRvAuTxt3, sRvAuTxt4, stCmtAuth, stRvAuth, sAllCmtAus, sAllRvAus, CmtMax, RvMax As String
    Dim CmtOne, RvOne, CmtMaxOp, RvMaxOp, CmtAuNum, RvAuNum, AuNumRet, RevNumRet, CmntCnter, RevCnter, CmntSmmry, RvSmmry As String
    Dim CmtAuArr() As String
    Dim RvAuArr() As String
    Dim strType, strPage, strAuthor, strSort As String
    Dim CmtMkrs As New Collection, a
    Dim RvMkrs As New Collection, g
    
    sCmAuTxt1 = "The following people have made comments:" & vbNewLine & vbNewLine: sCmAuTxt2 = vbNewLine & "Enter the name of the ": sCmAuTxt3 = "commenter to exclude, exactly as it appears above (without the list number)." & vbNewLine & vbNewLine & "Leaving this box empty will exit the macro.": sCmAuTxt4 = " reviewer to exclude"
    sRvAuTxt1 = "The following people have made tracked insertions or deletions:" & vbNewLine & vbNewLine: sRvAuTxt2 = vbNewLine & "Enter the name of the ": sRvAuTxt3 = "reviewer to exclude, exactly as it appears above." & vbNewLine & vbNewLine & "Leaving this box empty will exit the macro.": sRvAuTxt4 = " reviewer to exclude"
    
    Title = "Comment and revision tracker"
    n = 0
    rCount2 = 0
    Set oDoc = ActiveDocument
    nCount = ActiveDocument.Comments.Count
    rCount = oDoc.Revisions.Count
       
       Application.ScreenUpdating = False
    Selection.HomeKey Unit:=wdStory
    For w = 1 To rCount
        Selection.NextRevision
        If Selection.Range.Revisions(1).Type = wdRevisionDelete Or wdRevisionInsert Then
            rCount2 = rCount2 + 1
        Else
            GoTo Nextw
        End If
            
Nextw:
    Next w
    
    Selection.HomeKey Unit:=wdStory
    Application.ScreenUpdating = True
    
    If nCount = 0 Then
        initCSum = ""
    ElseIf nCount > 0 Then
        initCSum = "There are " & nCount & " comments in this document." & vbNewLine & vbNewLine
    End If
   
    If rCount2 = 0 Then
        initRSum = ""
    ElseIf rCount2 > 0 Then
        initRSum = "There are " & rCount2 & " eligible tracked insertions and deletions in this document." & vbNewLine & vbNewLine
    End If
    
    If (nCount = 0) And (rCount2 = 0) Then
        MsgBox "There are no comments or revisions to extract.", vbOKOnly + vbCritical, Title
        GoTo ExitHere
    End If
    
    If MsgBox("This macro can extract comments and tracked insertions" & vbNewLine & "or deletions but not other types of tracked changes." _
    & vbNewLine & vbNewLine & initCSum & initRSum & "Continue?", vbYesNo) = vbNo Then GoTo ExitHere
   
    If (rCount2 = 0) And (nCount > 0) Then
        finSel = "Comments"
        RvSmmry = ""
        GoTo ExclAuth
    ElseIf (rCount2 > 0) And (nCount = 0) Then
        finSel = "Tracks"
        CmntSmmry = ""
        GoTo Start
    ElseIf (rCount2 > 0) And (nCount > 0) Then
        selType = MsgBox("Do you want to extract both comments and revisions*?" & vbNewLine & vbNewLine & "Yes:" & vbTab & "Extract both" & vbNewLine & "No:" & vbTab & "To choose which to extract" & vbNewLine & "Cancel:" & vbTab & "To exit" & vbNewLine & vbNewLine & "*Only insertions and deletions will be extracted", vbYesNoCancel, "Customise extraction")
            If selType = vbCancel Then
                GoTo ExitHere
            ElseIf selType = vbYes Then
                finSel = "Both"
            ElseIf selType = vbNo Then
                selType2 = MsgBox("Do you want to extract comments or revisions?" & vbNewLine & vbNewLine & "Yes:" & vbTab & "Extract comments" & vbNewLine & "No:" & vbTab & "Extract revisions*" & vbNewLine & "Cancel:" & vbTab & "To exit" & vbNewLine & vbNewLine & "*Only insertions and deletions will be extracted", vbYesNoCancel, "Choose comments or revisions")
                    If selType2 = vbCancel Then
                        GoTo ExitHere
                    ElseIf selType2 = vbYes Then
                        finSel = "Comments"
                        RvSmmry = ""
                    ElseIf selType2 = vbNo Then
                        finSel = "Tracks"
                        CmntSmmry = ""
                    End If
            End If
    End If
    
ExclAuth:
    If Not finSel = "Tracks" Then
        blDimensioned = False
        For n = 1 To nCount
            stCmtAuth = ActiveDocument.Comments(n).Author
            If stCmtAuth <> "" Then
                If blDimensioned = True Then
                    ReDim Preserve CmtAuArr(0 To UBound(CmtAuArr) + 1) As String
                Else
                    ReDim CmtAuArr(0 To 0) As String
                    CmtAuArr(0) = ""
                    blDimensioned = True
                End If
                CmtAuArr(UBound(CmtAuArr)) = stCmtAuth
            End If
        Next
        
        sAllCmtAus = ""
        
        On Error Resume Next
        For Each a In CmtAuArr
            CmtMkrs.Add a, a
        Next
        
        For cax = 1 To CmtMkrs.Count
            sAllCmtAus = sAllCmtAus & cax & ". " & CmtMkrs(cax) & vbNewLine
        Next
        
        Erase CmtAuArr
        
        If CmtMkrs.Count > 5 Then
            CmtMax = 5
            CmtMaxOp = "You can exclude comments from a maximum of 5 people."
        ElseIf CmtMkrs.Count <= 5 Then
            CmtMax = CmtMkrs.Count - 1
        End If
        
        If CmtMax > 1 Then
            CmtMaxOp = "You can exclude comments from a maximum of " & CmtMax & " people."
        ElseIf CmtMax = 1 Then
            CmtMaxOp = "As there are only comments from 2 people, you can" & vbNewLine & "only choose to exclude a maximum of 1 person."
        ElseIf CmtMax = 0 Then
            CmtOne = MsgBox("There are only comments from 1 person, so you can't exclude any authors from the tracker.", vbOKCancel)
            If CmtOne = vbCancel Then
                GoTo ExitHere
            Else
                GoTo Start
            End If
        End If
        
        CmtAuNum = CmtMkrs.Count
        
        exAuth = MsgBox("There are comments from " & CmtAuNum & " different people." & vbNewLine & vbNewLine & "Do you want to exclude any commenters?", vbYesNoCancel + vbInformation, "Exclude authors")
        If exAuth = vbNo Then
            CmntSmmry = "All " & nCount & " comments from " & CmtAuNum & " authors were extracted." & vbNewLine & vbNewLine
            cTb = nCount
            If finSel = "Comments" Then
                GoTo Start
            ElseIf finSel = "Both" Then
                GoTo ExclRev
            End If
        ElseIf exAuth = vbCancel Then
            GoTo ExitHere
        ElseIf exAuth = vbYes Then
ChooseAuNum:
            If CmtMax = 1 Then
                exAuthNum = MsgBox(CmtMaxOp & vbNewLine & vbNewLine & "Click CANCEL to exit.", vbOKCancel, "Exclude author")
                If exAuthNum = vbOK Then
                    exAuthNum = 1
                ElseIf exAuthNum = vbCancel Then
                    GoTo ExitHere
                End If
            ElseIf CmtMax = 2 Or 3 Or 4 Or 5 Then
                exAuthNum = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & CmtMaxOp & vbNewLine & vbNewLine & "Enter the number of people to exclude below", "Number to exclude")
            End If
            
            If (exAuthNum = 0) Or (exAuthNum = "") Then
                AuNumRet = MsgBox("Do you want to continue without excluding any authors?" & vbNewLine & vbNewLine & "Click YES to proceed without excluding an author." & vbNewLine & vbNewLine & "Press NO to go back and input a valid number." & vbNewLine & vbNewLine & "Press CANCEL to exit", vbYesNoCancel + vbQuestion, "Error!")
                If AuNumRet = vbCancel Then
                    GoTo ExitHere
                ElseIf AuNumRet = vbYes Then
                    CmntSmmry = "All " & nCount & " comments from " & CmtAuNum & " authors were extracted." & vbNewLine & vbNewLine
                    GoTo Start
                ElseIf AuNumRet = vbNo Then
                    GoTo ChooseAuNum
                End If
            ElseIf (exAuthNum > CmtMaxOp) Or (IsNumeric(exAuthNum) = False) Then
                AuNumRet = MsgBox("You have entered an invalid value." & vbNewLine & vbNewLine & "Click RETRY to try again or CANCEL to exit", vbRetryCancel + vbCritical, "Error!")
                If AuNumRet = vbCancel Then
                    GoTo ExitHere
                ElseIf AuNumRet = vbRetry Then
                    GoTo ChooseAuNum
                End If
            End If
            
            If exAuthNum = 1 Then
                Auth2ex1 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & sCmAuTxt3, "Author to exclude")
                    If Auth2ex1 = "" Then End
                Auth2ex2 = "Null and void": Auth2ex3 = "Null and void": Auth2ex4 = "Null and void": Auth2ex5 = "Null and void"
            ElseIf exAuthNum = 2 Then
                Auth2ex1 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "1st " & sCmAuTxt3, "1st " & sCmAuTxt4)
                    If Auth2ex1 = "" Then End
                Auth2ex2 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "2nd " & sCmAuTxt3, "2nd " & sCmAuTxt4)
                    If Auth2ex2 = "" Then End
                Auth2ex3 = "Null and void": Auth2ex4 = "Null and void": Auth2ex5 = "Null and void"
            ElseIf exAuthNum = 3 Then
                Auth2ex1 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "1st " & sCmAuTxt3, "1st " & sCmAuTxt4)
                    If Auth2ex1 = "" Then End
                Auth2ex2 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "2nd " & sCmAuTxt3, "2nd " & sCmAuTxt4)
                    If Auth2ex2 = "" Then End
                Auth2ex3 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "3rd " & sCmAuTxt3, "3rd " & sCmAuTxt4)
                    If Auth2ex3 = "" Then End
                Auth2ex4 = "Null and void": Auth2ex5 = "Null and void"
            ElseIf exAuthNum = 4 Then
                Auth2ex1 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "1st " & sCmAuTxt3, "1st " & sCmAuTxt4)
                    If Auth2ex1 = "" Then End
                Auth2ex2 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "2nd " & sCmAuTxt3, "2nd " & sCmAuTxt4)
                    If Auth2ex2 = "" Then End
                Auth2ex3 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "3rd " & sCmAuTxt3, "3rd " & sCmAuTxt4)
                    If Auth2ex3 = "" Then End
                Auth2ex4 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "4th " & sCmAuTxt3, "4th " & sCmAuTxt4)
                    If Auth2ex4 = "" Then End
                Auth2ex5 = "Null and void"
            ElseIf exAuthNum = 5 Then
                Auth2ex1 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "1st " & sCmAuTxt3, "1st " & sCmAuTxt4)
                    If Auth2ex1 = "" Then End
                Auth2ex2 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "2nd " & sCmAuTxt3, "2nd " & sCmAuTxt4)
                    If Auth2ex2 = "" Then End
                Auth2ex3 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "3rd " & sCmAuTxt3, "3rd " & sCmAuTxt4)
                    If Auth2ex3 = "" Then End
                Auth2ex4 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "4th " & sCmAuTxt3, "4th " & sCmAuTxt4)
                    If Auth2ex4 = "" Then End
                Auth2ex5 = InputBox(sCmAuTxt1 & sAllCmtAus & vbNewLine & sCmAuTxt2 & "5th " & sCmAuTxt3, "5th " & sCmAuTxt4)
                    If Auth2ex5 = "" Then End
            Else
                End
            End If
        End If
        
CommCount:
    If exAuthNum = 1 Then
        CmntCnter = vbCr: cmCounter = Array(Auth2ex1)
    ElseIf exAuthNum = 2 Then
        CmntCnter = vbCr: cmCounter = Array(Auth2ex1, Auth2ex2)
    ElseIf exAuthNum = 3 Then
        CmntCnter = vbCr: cmCounter = Array(Auth2ex1, Auth2ex2, Auth2ex3)
    ElseIf exAuthNum = 4 Then
        CmntCnter = vbCr: cmCounter = Array(Auth2ex1, Auth2ex2, Auth2ex3, Auth2ex4)
    ElseIf exAuthNum = 5 Then
        CmntCnter = vbCr: cmCounter = Array(Auth2ex1, Auth2ex2, Auth2ex3, Auth2ex4, Auth2ex5)
    End If
    
    For b = LBound(cmCounter) To UBound(cmCounter)
        c = 0
        For d = 1 To nCount
            With oDoc.Comments(d)
                If .Author = cmCounter(b) Then c = c + 1
            End With
        Next
    Next
    
    sCmtTally = nCount - c: cTb = nCount - c
    
    CmntSmmry = "Extracted:" & vbTab & vbTab & vbTab & sCmtTally & " comments from " & (CmtAuNum - exAuthNum) & " authors." & vbNewLine & "Total in document:" & vbTab & vbTab & nCount & " comments from " & CmtAuNum & " authors." & vbNewLine & vbNewLine
    End If
    
    If finSel = "Comments" Then GoTo Start
ExclRev:
    If Not finSel = "Comments" Then
        blDimensioned = False
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        
        For x = 1 To rCount
            Selection.NextRevision
            If Selection.Range.Revisions(1).Type = wdRevisionDelete Or wdRevisionInsert Then
                With Selection.Range.Revisions(1)
                    stRvAuth = .Author
                    If stRvAuth <> "" Then
                        If blDimensioned = True Then
                            ReDim Preserve RvAuArr(0 To UBound(RvAuArr) + 1) As String
                        Else
                            ReDim RvAuArr(0 To 0) As String
                            RvAuArr(0) = ""
                            blDimensioned = True
                        End If
                        RvAuArr(UBound(RvAuArr)) = stRvAuth
                    End If
                End With
             End If
        Next x
        
       
        sAllRvAus = ""
        
        On Error Resume Next
        For Each g In RvAuArr
            RvMkrs.Add g, g
        Next
        
        For rax = 1 To RvMkrs.Count
            sAllRvAus = sAllRvAus & rax & ". " & RvMkrs(rax) & vbNewLine
        Next
        
        Erase RvAuArr
        
        If RvMkrs.Count > 5 Then
            RvMax = 5
            RvMaxOp = "You can exclude tracked insertions or deletions from a maximum of 5 people."
        ElseIf RvMkrs.Count <= 5 Then
            RvMax = RvMkrs.Count - 1
        End If
        
        If RvMax > 1 Then
            RvMaxOp = "You can exclude tracked insertions or deletions from a maximum of " & RvMax & " people."
        ElseIf RvMax = 1 Then
            RvMaxOp = "As there are only tracked insertions or deletions from 2 people, you can" & vbNewLine & "only choose to exclude a maximum of 1 person."
        ElseIf RvMax = 0 Then
            RvOne = MsgBox("There are only tracked insertions or deletions from 1 person, so you can't exclude any reviewers from the tracker.", vbOKCancel)
            If RvOne = vbCancel Then
                GoTo ExitHere
            Else
                GoTo Start
            End If
        End If
        
        RvAuNum = RvMkrs.Count
        
        exRev = MsgBox("There are tracked insertions or deletions from " & RvAuNum & " different people." & vbNewLine & vbNewLine & "Do you want to exclude any reviewers?", vbYesNoCancel + vbInformation, "Exclude reviewers")
        If exRev = vbNo Then
            RvSmmry = "All " & rCount2 & " tracked insertions or deletions from " & RvAuNum & " people were extracted." & vbNewLine & vbNewLine
            rTb = rCount2
            GoTo Start
        ElseIf exRev = vbCancel Then
            GoTo ExitHere
        ElseIf exRev = vbYes Then
ChooseRevNum:
            If RvMax = 1 Then
                exRevNum = MsgBox(RvMaxOp & vbNewLine & vbNewLine & "Click CANCEL to exit.", vbOKCancel, "Exclude reviewer")
                If exRevNum = vbOK Then
                    exRevNum = 1
                ElseIf exRevNum = vbCancel Then
                    GoTo ExitHere
                End If
            ElseIf RvMax = 2 Or 3 Or 4 Or 5 Then
                exRevNum = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & RvMaxOp & vbNewLine & vbNewLine & "Enter the number of people to exclude below", "Number to exclude")
            End If
            
            If (exRevNum = 0) Or (exRevNum = "") Then
                RevNumRet = MsgBox("Do you want to continue without excluding any reviewers?" & vbNewLine & vbNewLine & "Click YES to proceed without excluding a reviewer." & vbNewLine & vbNewLine & "Press NO to go back and input a valid number." & vbNewLine & vbNewLine & "Press CANCEL to exit", vbYesNoCancel + vbQuestion, "Error!")
                If RevNumRet = vbCancel Then
                    GoTo ExitHere
                ElseIf RevNumRet = vbYes Then
                    RvSmmry = "All " & rCount2 & " tracked insertions or deletions from " & RvAuNum & " people were extracted." & vbNewLine & vbNewLine
                    rTb = rCount2
                    GoTo Start
                ElseIf RevNumRet = vbNo Then
                    GoTo ChooseRevNum
                End If
            ElseIf (exRevNum > RvMaxOp) Or (IsNumeric(exRevNum) = False) Then
                RevNumRet = MsgBox("You have entered an invalid value." & vbNewLine & vbNewLine & "Click RETRY to try again or CANCEL to exit", vbRetryCancel + vbCritical, "Error!")
                If RevNumRet = vbCancel Then
                    GoTo ExitHere
                ElseIf RevNumRet = vbRetry Then
                    GoTo ChooseRevNum
                End If
            End If
            
            If exRevNum = 1 Then
                Rev2ex1 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & sRvAuTxt3, "Reviewer to exclude")
                    If Rev2ex1 = "" Then End
                Rev2ex2 = "Null and void": Rev2ex3 = "Null and void": Rev2ex4 = "Null and void": Rev2ex5 = "Null and void"
            ElseIf exRevNum = 2 Then
                Rev2ex1 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "1st " & sRvAuTxt3, "1st " & sRvAuTxt4)
                    If Rev2ex1 = "" Then End
                Rev2ex2 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "2nd " & sRvAuTxt3, "2nd " & sRvAuTxt4)
                    If Rev2ex2 = "" Then End
                Rev2ex3 = "Null and void": Rev2ex4 = "Null and void": Rev2ex5 = "Null and void"
            ElseIf exRevNum = 3 Then
                Rev2ex1 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "1st " & sRvAuTxt3, "1st " & sRvAuTxt4)
                    If Rev2ex1 = "" Then End
                Rev2ex2 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "2nd " & sRvAuTxt3, "2nd " & sRvAuTxt4)
                    If Rev2ex2 = "" Then End
                Rev2ex3 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "3rd " & sRvAuTxt3, "3rd " & sRvAuTxt4)
                    If Rev2ex3 = "" Then End
                Rev2ex4 = "Null and void": Rev2ex5 = "Null and void"
            ElseIf exRevNum = 4 Then
                Rev2ex1 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "1st " & sRvAuTxt3, "1st " & sRvAuTxt4)
                    If Rev2ex1 = "" Then End
                Rev2ex2 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "2nd " & sRvAuTxt3, "2nd " & sRvAuTxt4)
                    If Rev2ex2 = "" Then End
                Rev2ex3 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "3rd " & sRvAuTxt3, "3rd " & sRvAuTxt4)
                    If Rev2ex3 = "" Then End
                Rev2ex4 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "4th " & sRvAuTxt3, "4th " & sRvAuTxt4)
                    If Rev2ex4 = "" Then End
                Rev2ex5 = "Null and void"
            ElseIf exRevNum = 5 Then
                Rev2ex1 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "1st " & sRvAuTxt3, "1st " & sRvAuTxt4)
                    If Rev2ex1 = "" Then End
                Rev2ex2 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "2nd " & sRvAuTxt3, "2nd " & sRvAuTxt4)
                    If Rev2ex2 = "" Then End
                Rev2ex3 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "3rd " & sRvAuTxt3, "3rd " & sRvAuTxt4)
                    If Rev2ex3 = "" Then End
                Rev2ex4 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "4th " & sRvAuTxt3, "4th " & sRvAuTxt4)
                    If Rev2ex4 = "" Then End
                Rev2ex5 = InputBox(sRvAuTxt1 & sAllRvAus & vbNewLine & sRvAuTxt2 & "5th " & sRvAuTxt3, "5th " & sRvAuTxt4)
                    If Rev2ex5 = "" Then End
            Else
                End
            End If
        End If
        
RevCount:
    If exRevNum = 1 Then
        RevCnter = vbCr: revCounter = Array(Rev2ex1)
    ElseIf exRevNum = 2 Then
        RevCnter = vbCr: revCounter = Array(Rev2ex1, Rev2ex2)
    ElseIf exRevNum = 3 Then
        RevCnter = vbCr: revCounter = Array(Rev2ex1, Rev2ex2, Rev2ex3)
    ElseIf exRevNum = 4 Then
        RevCnter = vbCr: revCounter = Array(Rev2ex1, Rev2ex2, Rev2ex3, Rev2ex4)
    ElseIf exRevNum = 5 Then
        RevCnter = vbCr: revCounter = Array(Rev2ex1, Rev2ex2, Rev2ex3, Rev2ex4, Rev2ex5)
    End If
    
    For j = LBound(revCounter) To UBound(revCounter)
        k = 0
        
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        For y = 1 To rCount
            Selection.NextRevision
            If (Selection.Range.Revisions(1).Type = wdRevisionDelete Or wdRevisionInsert) _
                And (Selection.Range.Revisions(1).Author = revCounter(j)) Then k = k + 1
        Next y
    Next j
    
    Selection.HomeKey Unit:=wdStory
    Application.ScreenUpdating = True
    
    sRevTally = rCount2 - k: rTb = rCount2 = k
    
    RvSmmry = "Extracted:" & vbTab & vbTab & vbTab & sRevTally & " revisions from " & (RvAuNum - exRevNum) & " reviewers." & vbNewLine & "Total in document:" & vbTab & vbTab & rCount2 & " tracked insertions or deletions from" & vbNewLine & vbTab & vbTab & vbTab & RvAuNum & " people." & vbNewLine & vbNewLine
    End If
Start:
    MsgBox "Word may appear to freeze during this process!" & vbNewLine & vbNewLine & "Don't panic! Word has not crashed. Just wait for the process to finish." & vbNewLine & vbNewLine & "The more revisions and comments there are, the longer the process will take.", vbOKOnly, "DON'T PANIC!"
    Application.ScreenUpdating = False
    Set oNewDoc = Documents.Add
    oNewDoc.PageSetup.Orientation = wdOrientLandscape
    With oNewDoc
        .Content = ""
        If finSel = "Comments" Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=cTb + 1, _
                NumColumns:=7)
        ElseIf finSel = "Tracks" Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=rTb + 1, _
                NumColumns:=7)
        ElseIf finSel = "Both" Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=cTb + rTb + 1, _
                NumColumns:=7)
        End If
    End With
   
    If finSel = "Comments" Then
        oNewDoc.Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Comments extracted from: " & oDoc.Name
    ElseIf finSel = "Tracks" Then
        oNewDoc.Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Revisions extracted from: " & oDoc.Name
    ElseIf finSel = "Both" Then
        oNewDoc.Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Comments and revisions extracted from: " & oDoc.Name
    End If
    With oNewDoc.Styles(wdStyleNormal)
        .Font.Name = "Calibri"
        .Font.Size = 9
        .ParagraphFormat.LeftIndent = 0
        .ParagraphFormat.SpaceAfter = 6
    End With
   
    With oNewDoc.Styles(wdStyleHeader)
        .Font.Size = 8
        .ParagraphFormat.SpaceAfter = 0
    End With
    With oTable
        .Range.Style = wdStyleNormal
        .AllowAutoFit = False
        .PreferredWidthType = wdPreferredWidthPercent
        .PreferredWidth = 100
        .Columns.PreferredWidthType = wdPreferredWidthPercent
        .Columns(1).PreferredWidth = 5
        .Columns(2).PreferredWidth = 10
        .Columns(3).PreferredWidth = 25
        .Columns(4).PreferredWidth = 25
        .Columns(5).PreferredWidth = 15
        .Columns(6).PreferredWidth = 30
        .Columns(7).PreferredWidth = 2
        .Rows(1).HeadingFormat = True
    End With
    With oTable.Rows(1)
        .Range.Font.Bold = True
        .Cells(1).Range.Text = "Page"
        .Cells(2).Range.Text = "Type"
        .Cells(3).Range.Text = "Comment"
        .Cells(4).Range.Text = "Relevant text"
        .Cells(5).Range.Text = "Commenter"
        .Cells(6).Range.Text = "Action/response"
        .Cells(7).Range.Text = "Sort"
    End With
    
    If (finSel = "Both" Or finSel = "Comments") Then
        GoTo Comments
    Else
        If finSel = "Tracks" Then
            GoTo Tracks
        End If
    End If
   
Comments:
    For n = 1 To nCount
        If (oDoc.Comments(n).Author = Auth2ex1) Or (oDoc.Comments(n).Author = Auth2ex2) Or (oDoc.Comments(n).Author = Auth2ex3) Or (oDoc.Comments(n).Author = Auth2ex4) Or (oDoc.Comments(n).Author = Auth2ex5) Then
            GoTo NextN
        Else
            With oTable.Rows(n + 1)
                .Cells(1).Range.Text = _
                    oDoc.Comments(n).Scope.Information(wdActiveEndPageNumber)
                .Cells(2).Range.Text = "Comment"
                .Cells(3).Range.Text = oDoc.Comments(n).Range.Text
                .Cells(4).Range.Text = oDoc.Comments(n).Scope
                .Cells(5).Range.Text = oDoc.Comments(n).Author
                .Cells(7).Range.Text = oDoc.Comments(n).Scope.Information(wdFirstCharacterLineNumber)
            End With
            GoTo NextN
        End If
NextN:
    Next n
    
    If finSel = "Comments" Then
        GoTo Finalise
    Else
        GoTo Tracks
    End If
Tracks:
    Selection.HomeKey Unit:=wdStory
    For z = 1 To rCount
        Selection.NextRevision
        With Selection.Range.Revisions(1)
            If (.Type <> wdRevisionDelete Or wdRevisionInsert) Or (.Author = (Rev2ex1 Or Rev2ex2 Or Rev2ex3 Or Rev2ex4 Or Rev2ex5)) Then
                    GoTo Nextz
            Else
                Select Case .Type
                    Case wdRevisionInsert
                        strPage = .Range.Information(wdActiveEndPageNumber)
                        strType = "Insert"
                        strAuthor = .Author
                        strSort = .Range.Information(wdFirstCharacterLineNumber)
                        strText = .Range.Text
                        oRange = .Range
                        Do While InStr(1, oRange.Text, Chr(2)) > 0
                            i = InStr(1, strText, Chr(2))
                                If oRange.Footnotes.Count = 1 Then
                                   strText = Replace(Expression:=strText, _
                                            Find:=Chr(2), Replace:="[footnote reference]", _
                                            Start:=1, Count:=1)
                                    oRange.Start = oRange.Start + i
                                ElseIf oRange.Endnotes.Count = 1 Then
                                   strText = Replace(Expression:=strText, _
                                            Find:=Chr(2), Replace:="[endnote reference]", _
                                            Start:=1, Count:=1)
                                    oRange.Start = oRange.Start + i
                                End If
                        Loop
                        Set oRows = oTable.Rows.Add
                        With oRows
                            .Cells(1).Range.Text = strPage
                            With .Cells(2).Range
                                .Text = strType
                                .Font.Color = wdColorBlue
                            End With
                            With .Cells(4).Range
                                .Text = strText
                                .Font.Color = wdColorBlue
                            End With
                            .Cells(5).Range.Text = strAuthor
                            .Cells(7).Range.Text = strSort
                        End With
                    Case wdRevisionInsert
                        strPage = .Range.Information(wdActiveEndPageNumber)
                        strType = "Delete"
                        strAuthor = .Author
                        strSort = .Range.Information(wdFirstCharacterLineNumber)
                        strText = .Range.Text
                        oRange = .Range
                        Do While InStr(1, oRange.Text, Chr(2)) > 0
                            i = InStr(1, strText, Chr(2))
                                If oRange.Footnotes.Count = 1 Then
                                   strText = Replace(Expression:=strText, _
                                            Find:=Chr(2), Replace:="[footnote reference]", _
                                            Start:=1, Count:=1)
                                    oRange.Start = oRange.Start + i
                                ElseIf oRange.Endnotes.Count = 1 Then
                                   strText = Replace(Expression:=strText, _
                                            Find:=Chr(2), Replace:="[endnote reference]", _
                                            Start:=1, Count:=1)
                                    oRange.Start = oRange.Start + i
                                End If
                        Loop
                        Set oRows = oTable.Rows.Add
                        With oRows
                            .Cells(1).Range.Text = strPage
                            With .Cells(2).Range
                                .Text = strType
                                .Font.Color = wdColorRed
                            End With
                            With .Cells(4).Range
                                .Text = strText
                                .Font.Color = wdColorRed
                            End With
                            .Cells(5).Range.Text = strAuthor
                            .Cells(7).Range.Text = strSort
                        End With
                End Select
            End If
        End With
Nextz:
    Next z
  
Finalise:
   
    Set myTable = ActiveDocument.Tables(1)
    With myTable.Borders
        .InsideLineStyle = wdLineStyleSingle
        .OutsideLineStyle = wdLineStyleSingle
    End With
    
    ActiveDocument.Tables(1).Select
    
    Selection.Sort ExcludeHeader:=True, FieldNumber:="Column 1", SortFieldType _
        :=wdSortFieldNumeric, SortOrder:=wdSortOrderAscending, FieldNumber2:= _
        "Column 7", SortFieldType2:=wdSortFieldNumeric, SortOrder2:= _
        wdSortOrderAscending, FieldNumber3:="", SortFieldType3:= _
        wdSortFieldAlphanumeric, SortOrder3:=wdSortOrderAscending, Separator:= _
        wdSortSeparateByCommas, SortColumn:=False, CaseSensitive:=False, _
        LanguageID:=wdEnglishUK, SubFieldNumber:="Paragraphs", SubFieldNumber2:= _
        "Paragraphs", SubFieldNumber3:="Paragraphs"
        
    Selection.Columns(7).Delete
    
    With ActiveDocument.Tables(1)
        noCol = .Range.Rows(1).Cells.Count
            For blRows = .Rows.Count To 1 Step -1
                With .Rows(blRows)
                    If Len(.Range) = noCol * 2 + 2 Then .Delete
                End With
            Next blRows
    End With
    
    Application.ScreenUpdating = True
    Application.ScreenRefresh
          
    oNewDoc.Activate
    MsgBox CmntSmmry & RvSmmry & "Finished creating tracker.", vbOKOnly + vbInformation, "Job summary"
    
ExitHere:
    Set oDoc = Nothing
    Set oNewDoc = Nothing
    Set oTable = Nothing
   
End Sub
macropod
06-28-2018, 02:21 PM
Instead of trying to combine everything into a single code module, you should have three modules; one for the revisions; one for the comments; and one for the decision-making that calls either/both of the others as appropriate. Where necessary, the first two should use their own variables (e.g. for counters); you can use global variables for things like the names if they're to be shared by the first two modules.
h2whoa
06-29-2018, 01:20 AM
Ah, interesting. I'm still an amateur just tweaking things without a deep understanding, so hadn't considered separating it into three modules. Appreciate your help. I'll give this a try.
So, if my decision module gets the Author names held in a String, like Auth2ex1, how would I pass that value into the next module (i.e. the comment module)?
Thanks again.
macropod
06-29-2018, 04:59 AM
For example:
Dim StrAuth As String, i As Long
Sub Main()
Dim Rslt
StrAuth = InputBox("Input Authors, separated by | (e.g. AuthA|AuthB)")
Select Case MsgBox("Process OptionA = Yes" & vbCr & "Process OptionB = No" & vbCr & "Process OptionB = Cancel", vbYesNoCancel)
  Case vbYes: MsgBox "You chose OptionA": Call OptionA
  Case vbNo: MsgBox "You chose OptionB": Call OptionB
  Case vbCancel: MsgBox "You chose OptionA & OptionB": Call OptionA: Call OptionB
End Select
End Sub
Sub OptionA()
For i = 0 To UBound(Split(StrAuth, "|"))
  MsgBox " OptionA " & Split(StrAuth, "|")(i)
Next
End Sub
Sub OptionB()
For i = 0 To UBound(Split(StrAuth, "|"))
  MsgBox " OptionB " & Split(StrAuth, "|")(i)
Next
End Sub
Kilroy
06-29-2018, 05:11 AM
H2Whoa what an amazing and useful tool this would be. I hope someone can figure out the table population issue.
h2whoa
06-29-2018, 05:58 AM
Great, thanks Paul. I'll give this a whirl.
Cheers.
h2whoa
06-29-2018, 05:59 AM
H2Whoa what an amazing and useful tool this would be. I hope someone can figure out the table population issue.
I'll keep you posted! I feel like it's nearly there.
Kilroy
06-29-2018, 11:22 AM
Try this. in the Comments section:
Comments:
    For n = 1 To nCount
        If (oDoc.Comments(n).Author = Auth2ex1) Or (oDoc.Comments(n).Author = Auth2ex2) Or (oDoc.Comments(n).Author = Auth2ex3) Or (oDoc.Comments(n).Author = Auth2ex4) Or (oDoc.Comments(n).Author = Auth2ex5) Then
            GoTo NextN
        Else
            oTable.Rows.Add
            With oTable.Rows(n + 1)
                .Cells(1).range.Text = _
                    oDoc.Comments(n).Scope.Information(wdActiveEndPageNumber)
                .Cells(2).range.Text = "Comment"
                .Cells(3).range.Text = oDoc.Comments(n).range.Text
                .Cells(4).range.Text = oDoc.Comments(n).Scope
                .Cells(5).range.Text = oDoc.Comments(n).Author
                .Cells(7).range.Text = oDoc.Comments(n).Scope.Information(wdFirstCharacterLineNumber)
            End With
            GoTo NextN
        End If
I just added " oTable.Rows.Add"
Kilroy
06-29-2018, 11:39 AM
Unfortunately it is not populating the table with the tracked changes, just the comments are working. I'll look at it more when I get home from work.
macropod
06-29-2018, 06:03 PM
You might be interested in the revision & comment extraction macros I posted at: https://answers.microsoft.com/en-us/office/forum/office_2007-word/possible-to-export-word-track-changes-information/e0dee9dc-aedb-41d3-92bf-8dc609cc75af. See my posts of November 3, 2014 & September 5, 2015, respectively.
h2whoa
07-01-2018, 12:57 PM
Unfortunately it is not populating the table with the tracked changes, just the comments are working. I'll look at it more when I get home from work.
Yeah, it's so frustrating. I just don't know why it's refusing to cooperate with the tracked changes! Will also take a look at macropod's macros.
Kilroy
07-04-2018, 08:48 AM
I couldn't figure it out but I did put this together today. No options but it works.
Sub CommentsAndRevisionsToTable()
'Kilroy
Dim s As String
Dim r As String
Dim cmt As Word.Comment
Dim doc As Word.Document
Dim rev As Word.Revision
Dim oTbl As Table
For Each cmt In ActiveDocument.Comments
s = s & cmt.Author & (",Comment " & cmt.Index) & "," & cmt.range.Text & vbCr
Next
For Each rev In ActiveDocument.Revisions
r = r & rev.Author & (",Revision " & rev.Index) & "," & rev.range.Text & vbCr  
Next
Set doc = Documents.Add
doc.range.Text = s & r
  Selection.WholeStory
    Selection.ConvertToTable Separator:=wdSeparateByCommas, NumColumns:=3, _
        numRows:=12, AutoFitBehavior:=wdAutoFitFixed
    With Selection.Tables(1)
        If .Style <> "Table Grid" Then
            .Style = "Table Grid"
        End If
        
    End With
    Selection.InsertRowsAbove 1
  With Selection.Tables(1).Columns(3)
  .Select
Selection.InsertColumnsRight
End With
With Selection.Tables(1)
.Columns(1).SetWidth ColumnWidth:=100, _
RulerStyle:=wdAdjustFirstColumn
.Columns(2).SetWidth ColumnWidth:=100, _
RulerStyle:=wdAdjustFirstColumn
.Columns(3).SetWidth ColumnWidth:=100, _
RulerStyle:=wdAdjustFirstColumn
.Columns(4).SetWidth ColumnWidth:=100, _
RulerStyle:=wdAdjustFirstColumn
.Cell(1, 1).range.Text = "Author"
.Cell(1, 2).range.Text = "Edit Type"
.Cell(1, 3).range.Text = "Comment/Revision"
.Cell(1, 4).range.Text = "Acceptable?"
End With
End Sub
Kilroy
07-04-2018, 02:02 PM
I know VBA can't tell what a "sentence" is but is there a way to include in the revision portion, an entire sentence using something like selection.start and selection.end? Ist here something else?
h2whoa
07-05-2018, 11:31 PM
Interesting idea. And thanks for the code. Will take a look today.
Kilroy
07-06-2018, 04:48 AM
Really the most ideal layout would include the before and after "sentence".
h2whoa
07-09-2018, 09:46 AM
Update:
I have had a significant breakthrough with this. I need to tidy up a few things as I'd be embarrassed to post the code in it's current working form, but I have actually managed to get it working. Furthermore, in my updated code the only limit on the number of people you can choose to exclude is the number of reviewers and commenters in the document. I'll post the code in the next couple of days.
h2whoa
07-10-2018, 09:14 AM
Well. Here we go. Wow, this has had me smashing my head into my desk on numerous occasions. It's not pretty, but it seems to work. Three things to consider:
 I'm quite sure that this is not 'pretty' and that somebody who actually knows what they are doing would be able to make this much more elegant than my fudge.
 This will only extract comments and tracked text insertions or deletions. During the course of this I found out that revision handling isn't great in VBA, so I had to add a Like test for revisions to only select text ranges to prevent failures.
 If your document is large and/or contains extensive revisions, Word may appear to freeze at various points in this process. In the last stage, when it's building the table, Word may appear to lock up for a good few minutes, especially if there are lots of revisions. This is normal. Just leave it to run and it will get there.
As mentioned in the top post of this thread, I'm indebted to the brains and helpfulness of others for getting me to this point. If you have any ideas for tidying up this behemoth and making it more efficient, please just let me know!
As suggested by macropod, I've split this out into a number of subs, each one handling a specific part of the process.
'Public declarations
Public cmInc, cmEx, comSkip, revInc, revEx, revSkip As Boolean
Public cmSummary, revSummary, scrllPs As String
Public nCount, lAn, lFAn, cmTally, _
        rCount, indelCount, lRn, lFRevn, revTally As Long
Public crsRng As Range
Public nc2, rev2exN As Integer
Public Cmt2ex As New Collection, cd
Public Review2ex As New Collection, rd
Public Cmt2exArr() As String
Public Rev2exArr() As String
Public oDoc As Document
Public Sub Comment_And_InDel_Grid()
i_Reset_Pub_Decs
ii_Com_Analyse
iii_Rev_Analyse
iv_Grid_maker
End Sub
Public Sub i_Reset_Pub_Decs()
cmInc = False: cmEx = False: comSkip = False: revInc = False: revEx = False: revSkip = False
cmSummary = "": revSummary = "": scrllPs = ""
nCount = 0: lAn = 0: lFAn = 0: cmTally = 0: rCount = 0: indelCount = 0: lRn = 0: lFRevn = 0: revTally = 0
Set crsRng = Nothing
nc2 = 0: rev2exN = 0
Set Cmt2ex = Nothing
Set Review2ex = Nothing
Erase Cmt2exArr
Erase Rev2exArr
Set oDoc = Nothing
End Sub
Public Sub ii_Com_Analyse()
    Dim b, c, e, g, h, i, j As Long
    Dim sCmAuTxt1, initCSum, chsEx, stCmtAuth, sTCmAs, _
        rtrn2ex, rtrn2exsel, cmtMax, selComs, stSkpRv, C2X As String
    Dim CmtAuArr() As String
    Dim CmtCol As New Collection, ca
    sCmAuTxt1 = "The following people have made comments:" & vbNewLine & vbNewLine
    Set oDoc = ActiveDocument
    nCount = ActiveDocument.Comments.Count
    rCount = ActiveDocument.Revisions.Count
    cmInc = False
    comSkip = False
    Set crsRng = Selection.Range
    scrllPs = ActiveWindow.ActivePane.VerticalPercentScrolled
    
    If (nCount = 0) And (rCount > 0) Then
        MsgBox "There are no comments in this document.", vbOKOnly + vbCritical
        cmInc = False: cmEx = False: comSkip = True
        Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
        Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
        GoTo Revcheck
    ElseIf (nCount = 0) And (rCount = 0) Then
        MsgBox "There are no comments or changes in this document in this document.", vbOKOnly + vbCritical
        Set oDoc = Nothing
        End
    ElseIf nCount = 1 Then
        initCSum = "There is only one comment in this document." & vbNewLine & vbNewLine & "Do you want to include this in the tracker?"
        lAn = 1
        cmtMax = "There is only one author, so you can't exclude them from the tracker."
    ElseIf nCount > 1 Then
        'Compiles a list of people who have made comments in the document
        blDimensioned = False
        For b = 1 To nCount
            stCmtAuth = ActiveDocument.Comments(b).Author
            If stCmtAuth <> "" Then
                If blDimensioned = True Then
                    ReDim Preserve CmtAuArr(0 To UBound(CmtAuArr) + 1) As String
                Else
                    ReDim CmtAuArr(0 To 0) As String
                    CmtAuArr(0) = ""
                    blDimensioned = True
                End If
                CmtAuArr(UBound(CmtAuArr)) = stCmtAuth
            End If
        Next
        
        'Collects and counts authors
        On Error Resume Next
        For Each ca In CmtAuArr
            CmtCol.Add ca, ca
        Next
        
        lAn = CmtCol.Count
        
        'Commenter exclusion text building
        If CmtCol.Count = 1 Then
            cmtMax = "There is only one author, so you can't exclude them from the tracker."
            initCSum = "There are " & nCount & " comments from " & CmtCol(1) & "." & vbNewLine & vbNewLine & "Do you want to include comments in the tracker?"
        ElseIf CmtCol.Count > 1 Then
            sTCmAs = ""
            For c = 1 To lAn
                sTCmAs = sTCmAs & c & ". " & CmtCol(c) & vbNewLine
            Next
            
            initCSum = "There are " & nCount & " comments from " & lAn & " people." & vbNewLine & sCmAuTxt1 & sTCmAs & vbNewLine _
            & vbNewLine & "Do you want to include comments in the tracker?"
            
            If CmtCol.Count > 2 Then
                lFAn = CmtCol.Count - 1
                cmtMax = "You can exclude comments from a maximum of " & lFAn & " people." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
            ElseIf CmtCol.Count = 2 Then
                lFAn = 1
                cmtMax = "You can exclude comments from a maximum of one person." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
            End If
        End If
    End If
    
    'Decide whether to include comments in the tracker
    selComs = MsgBox(initCSum, vbYesNo + vbQuestion)
    
    If selComs = vbYes Then
        cmInc = True
    ElseIf selComs = vbNo Then
        comSkip = True: cmInc = False: cmEx = False
        Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
        Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
        GoTo Revcheck
    End If
Revcheck:
    If rCount > 0 Then
        stSkpRv = MsgBox("Will you also want to process tracked changes?", vbYesNo + vbQuestion)
        If stSkpRv = vbYes Then
            revSkip = False: revInc = True
        ElseIf stSkpRv = vbNo Then
            revSkip = True
            revInc = False: revEx = False
            Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
            Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
        End If
        If comSkip = True Then GoTo EndComCount
    ElseIf rCount = 0 Then
        MsgBox "There are no tracked changes in this document. Only comments will be extracted.", vbOKOnly + vbInformation
        revSkip = True
        revInc = False: revEx = False
        Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
        Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
    End If
        
    If lAn = 1 Then
        If MsgBox(cmtMax, vbOKCancel + vbInformation) = vbOK Then
            cmInc = True: cmEx = False
            Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
            Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
            cmSummary = "All " & nCount & " comments from " & CmtCol(1) & " extracted."
            GoTo EndComCount
        Else
            cmInc = False: cmEx = False
            Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
            Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
            GoTo EndComCount
        End If
    Else
        'Choose whether to exclude any commenters
        chsEx = MsgBox(sCmAuTxt1 & sTCmAs & vbNewLine & cmtMax, vbYesNoCancel)
        If chsEx = vbYes Then
            cmEx = True
n2ex:
            'Choose number of commenters to exclude
            nc2 = InputBox(sCmAuTxt1 & sTCmAs & vbNewLine & "How many people do you want to exclude?" & vbNewLine & vbNewLine & "Maximum of " & lFAn & ".", "Number to exclude")
            
            'Number validity testing
            If (IsNumeric(nc2) = False) Or (nc2 > (CmtCol.Count - 1)) Or (nc2 = 0) Then
                rtrn2ex = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract comments" _
                & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                If rtrn2ex = vbRetry Then
                    GoTo n2ex
                
                ElseIf rtrn2ex = vbAbort Then
                    cmInc = False: cmEx = False
                    Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
                    Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
                    GoTo EndComCount
                
                ElseIf rtrn2ex = vbIgnore Then
                    cmInc = True: cmEx = False
                    Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
                    Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
                    cmSummary = "All " & nCount & " comments extracted."
                    GoTo EndComCount
                End If
            Else
                'Build user-defined list of commenters to exclude
                blDimensioned = False
                For e = 1 To nc2
Exn:
                    j = InputBox(sCmAuTxt1 & sTCmAs & vbNewLine & "Enter the number of the person to exclude, from the list above.")
                        If (j > CmtCol.Count) Or (j = 0) Or (IsNumeric(j) = False) Then
                            rtrn2exsel = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract comments" _
                                        & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                                        & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                                        
                                        If rtrn2exsel = vbRetry Then
                                        GoTo Exn
                                        
                                        ElseIf rtrn2exsel = vbAbort Then
                                            cmInc = False: cmEx = False
                                            Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
                                            Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
                                            GoTo EndComCount
                                        
                                        ElseIf rtrn2exsel = vbIgnore Then
                                            cmInc = True: cmEx = False
                                            Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
                                            Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
                                            cmSummary = "All " & nCount & " comments extracted."
                                            GoTo EndComCount
                                        End If
                            Else
                            
                                C2X = CmtCol(j)
                                
                    
                                If blDimensioned = True Then
                                    ReDim Preserve Cmt2exArr(0 To UBound(Cmt2exArr) + 1) As String
                                Else
                                    ReDim Cmt2exArr(0 To 0) As String
                                    Cmt2exArr(0) = ""
                                    blDimensioned = True
                                End If
                                Cmt2exArr(UBound(Cmt2exArr)) = C2X
                            End If
                Next
                
                
                On Error Resume Next
                For Each cd In Cmt2exArr
                    Cmt2ex.Add cd, cd
                Next
                
                'Counts number of comments made by authors to exclude
                For g = LBound(Cmt2exArr) To UBound(Cmt2exArr)
                    h = 0
                    For i = 1 To nCount
                        With oDoc.Comments(i)
                            If .Author = Cmt2exArr(g) Then h = h + 1
                        End With
                    Next
                Next
                
                'Counts number of comments that are included in the tracker
                cmTally = nCount - h
                
                cmSummary = "Extracted:" & vbTab & vbTab & vbTab & cmTally & " comments from " & Cmt2ex.Count & " people." & vbNewLine _
                            & "Total in document:" & vbTab & vbTab & nCount & " comments from" & vbNewLine _
                            & vbTab & vbTab & vbTab & lAn & " people." & vbNewLine & vbNewLine
            
            End If
        
        ElseIf chsEx = vbNo Then
            cmInc = True: cmEx = False
            Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
            Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
            cmSummary = "All " & nCount & " comments from " & CmtCol(1) & " extracted."
            GoTo EndComCount
        ElseIf chsEx = vbCancel Then
            cmInc = False: cmEx = False
            Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
            Cmt2exArr(UBound(Cmt2exArr)) = "ZilchCom 2"
            GoTo EndComCount
        End If
    End If
EndComCount:
End Sub
Public Sub iii_Rev_Analyse()
Dim b, c, e, g, h, i, n As Long
    Dim sReviewerTxt1, initRevSum, chsRevEx, stReviewer, sTReviewrs, _
        rtrn2Revex, revMax, selRevs, rtrnrvlist, R2X As String
    Dim ReviewerArr() As String
    Dim RevCol As New Collection, ra
    If revSkip = True Then GoTo EndRevCount
    
    sReviewerTxt1 = "The following people have made tracked insertions/deletions:" & vbNewLine & vbNewLine
    revInc = False
    
    If rCount = 1 Then
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        Selection.NextRevision.Range.Select
        With Selection.Range.Revisions(1)
            If .Type = wdRevisionDelete Or wdRevisionInsert Then
                initRevSum = "There is only one tracked insertion/deletion in this document." & vbNewLine & vbNewLine & "Do you want to include this in the tracker?"
                revMax = "There is only one reviewer, so you can't exclude them from the tracker."
                lRn = 1
            Else
                crsRng.Select
                ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
                Application.ScreenUpdating = True
                MsgBox "There are no tracked insertions/deletions in this document.", vbOKOnly + vbCritical
                revInc = False
                End
            End If
        End With
        crsRng.Select
        ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
        Application.ScreenUpdating = True
    ElseIf rCount > 1 Then
        'Compiles a list of people who have made changes in the document
        
        MsgBox "Note: Word may appear to freeze at various points. Please be patient." & vbNewLine & vbNewLine & _
                "The more tracked changes there are, the longer the freezes will be.", vbOKOnly + vbInformation, "Word is now processing tracked changes"
        
        Application.Screenrefresh
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        
        indelCount = 0
        
        blDimensioned = False
        For b = 1 To rCount
            Selection.NextRevision
            With Selection.Range.Revisions(1)
                If ((.Type = wdRevisionDelete) Or (.Type = wdRevisionInsert)) _
                And (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") Then
                    indelCount = indelCount + 1
                    stReviewer = .Author
                    If stReviewer <> "" Then
                        If blDimensioned = True Then
                            ReDim Preserve ReviewerArr(0 To UBound(ReviewerArr) + 1) As String
                        Else
                            ReDim ReviewerArr(0 To 0) As String
                            ReviewerArr(0) = ""
                            blDimensioned = True
                        End If
                        ReviewerArr(UBound(ReviewerArr)) = stReviewer
                    End If
                End If
            End With
        Next
        
        crsRng.Select
        ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
        Application.ScreenUpdating = True
        
        'Collects and counts reviewers
        On Error Resume Next
        For Each ra In ReviewerArr
            RevCol.Add ra, ra
        Next
        
        lRn = RevCol.Count
        
        'Reviewer exclusion text building
        If RevCol.Count = 1 Then
            revMax = "There is only one reviewer, so you can't exclude them from the tracker."
            initRevSum = "There are " & indelCount & " tracked insertions/deletions from " & RevCol(1) & "." & vbNewLine & vbNewLine & "Do you want to include tracked changes in the tracker?"
        ElseIf RevCol.Count > 1 Then
            sTReviewrs = ""
            For c = 1 To lRn
                sTReviewrs = sTReviewrs & c & ". " & RevCol(c) & vbNewLine
            Next
            
            initRevSum = "There are " & indelCount & " tracked insertions/deletions from " & lRn & " people." & vbNewLine & sReviewerTxt1 & sTReviewrs & vbNewLine _
            & vbNewLine & "Do you want to include tracked changes in the tracker?"
            
            If RevCol.Count > 2 Then
                lFRevn = RevCol.Count - 1
                revMax = "You can exclude tracked insertions/deletions from a maximum of " & lFRevn & " people." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
            ElseIf RevCol.Count = 2 Then
                lFRevn = 1
                revMax = "You can exclude tracked insertions/deletions from a maximum of one person." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
            End If
        End If
    End If
    
    'Decide whether to include tracked changes in the tracker
    selRevs = MsgBox(initRevSum, vbYesNo + vbQuestion)
    
    If selRevs = vbYes Then
        revInc = True
    ElseIf selRevs = vbNo Then
        revInc = False: revEx = False
        Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
        Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
        GoTo EndRevCount
    End If
        
    If lRn = 1 Then
        If MsgBox(revMax, vbOKCancel + vbInformation) = vbOK Then
            revInc = True: revEx = False
            Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
            Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
            revSummary = "All " & indelCount & " tracked insertions/deletions from " & RevCol(1) & " extracted."
            GoTo EndRevCount
        Else
            revInc = False: revEx = False
            Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
            Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
            GoTo EndRevCount
        End If
    Else
        'Choose whether to exclude any reviewers
        chsRevEx = MsgBox(sReviewerTxt1 & sTReviewrs & vbNewLine & revMax, vbYesNoCancel)
        If chsRevEx = vbYes Then
            revEx = True
nrv2ex:
            'Choose number of reviewers to exclude
            rev2exN = InputBox(sReviewerTxt1 & sTReviewrs & vbNewLine & "How many people do you want to exclude?" & vbNewLine & vbNewLine & "Maximum of " & lFRevn & ".", "Number to exclude")
            
            'Number validity testing
            If (IsNumeric(rev2exN) = False) Or (rev2exN > (RevCol.Count - 1)) Or (rev2exN < 1) Then
                rtrn2Revex = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract revisions" _
                & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                If rtrn2Revex = vbRetry Then
                    GoTo nrv2ex
                ElseIf rtrn2Revex = vbAbort Then
                    revInc = False: revEx = False
                    Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
                    Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
                    GoTo EndRevCount
                ElseIf rtrn2Revex = vbIgnore Then
                    revInc = True: revEx = False
                    Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
                    Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
                    revSummary = "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted."
                    GoTo EndRevCount
                End If
            Else
                'Build user-defined list of reviewers to exclude
                blDimensioned = False
                For e = 1 To rev2exN
Revexlist:
                    n = InputBox(sReviewerTxt1 & sTReviewrs & vbNewLine & "Enter the number of the person to exclude, exactly " & _
                                vbNewLine & "as it appears in the list above.")
                        If (n > RevCol.Count) Or (n = 0) Or (IsNumeric(n) = False) Then
                            rtrnrvlist = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract revisions" _
                                        & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                                        & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                                        
                                        If rtrn2Revex = vbRetry Then
                                            GoTo Revexlist
                                        ElseIf rtrn2Revex = vbAbort Then
                                            revInc = False: revEx = False
                                            Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
                                            Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
                                            GoTo EndRevCount
                                        ElseIf rtrn2Revex = vbIgnore Then
                                            revInc = True: revEx = False
                                            Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
                                            Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
                                            revSummary = "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted."
                                            GoTo EndRevCount
                                        End If
                        Else
                            R2X = RevCol(n)
                            
                            If blDimensioned = True Then
                                ReDim Preserve Rev2exArr(0 To UBound(Rev2exArr) + 1) As String
                            Else
                                ReDim Rev2exArr(0 To 0) As String
                                Rev2exArr(0) = ""
                                blDimensioned = True
                            End If
                            Rev2exArr(UBound(Rev2exArr)) = R2X
                        End If
                Next
                
                On Error Resume Next
                For Each rd In Rev2exArr
                    Review2ex.Add rd, rd
                Next
                
                
                'Counts number of changes made by reviewers to exclude
                Application.ScreenUpdating = False
                Selection.HomeKey Unit:=wdStory
                
                
                h = 0
                For i = 1 To rCount
                    With Selection.NextRevision
                        If .Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*" Then
                            For g = LBound(Rev2exArr) To UBound(Rev2exArr)
                                If .Author = Rev2exArr(g) Then h = h + 1
                            Next
                        End If
                    End With
                Next
                
                
                crsRng.Select
                ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
                Application.ScreenUpdating = True
                Application.Screenrefresh
                
                
                'Counts number of changes that are included in the tracker
                revTally = indelCount - h
                
                revSummary = "Extracted:" & vbTab & vbTab & vbTab & revTally & " tracked insertions/deletions" & vbNewLine _
                            & vbTab & vbTab & vbTab & "from " & Review2ex.Count & " people." & vbNewLine & "Total in document:" _
                            & vbTab & vbTab & indelCount & " tracked insertions/deletions" & vbNewLine _
                            & vbTab & vbTab & vbTab & "from " & lRn & " people." & vbNewLine & vbNewLine
            
            End If
            
        ElseIf chsRevEx = vbNo Then
            revInc = True: revEx = False
            Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
            Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
            revSummary = "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted."
            GoTo EndRevCount
        ElseIf chsRevEx = vbCancel Then
            revInc = False: revEx = False
            Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
            Rev2exArr(UBound(Rev2exArr)) = "ZilchRev 2"
            GoTo EndRevCount
        End If
    End If
EndRevCount:
End Sub
Public Sub iv_Grid_maker()
    Dim oNewDoc As Document
    Dim oTable As Table
    Dim NXTA, NXTR As Boolean
    Dim f, i, j, n, rvb, _
        blRows, exRows, rve, rvf, rvg, rvr, rparCount, rrcnt As Long
    Dim Rvtype, Rvpage, Rvsort, Rvauth As String
    
    Title = "Comment and revision tracker"
    Set oDoc = ActiveDocument
    rCount = oDoc.Revisions.Count
    
    Application.Screenrefresh
    
    If cmInc = False And revInc = False Then
        MsgBox "No comments or revisions selected.", vbOKOnly + vbInformation
        GoTo ExitHere
    End If
    
       
Start:
    Application.Screenrefresh
    MsgBox "Word may appear to freeze during this process!" & vbNewLine & vbNewLine & "Don't panic! Word has not crashed. Just wait for the process to finish." & vbNewLine & vbNewLine & "The more revisions and comments there are, the longer the process will take.", vbOKOnly, "DON'T PANIC!"
    Application.ScreenUpdating = False
    Set oNewDoc = Documents.Add
    oNewDoc.PageSetup.Orientation = wdOrientLandscape
    With oNewDoc
        .Content = ""
        If cmInc = True And revInc = False Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=nCount + 1, _
                NumColumns:=7)
                
            .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Comments extracted from: " & oDoc.Name
            
        ElseIf cmInc = False And revInc = True Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=rCount + 1, _
                NumColumns:=7)
                
            .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Revisions extracted from: " & oDoc.Name
                
        ElseIf cmInc = True And revInc = True Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=nCount + rCount + 1, _
                NumColumns:=7)
                
            .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Comments and revisions extracted from: " & oDoc.Name
                
        End If
    End With
    With oNewDoc.Styles(wdStyleNormal)
        .Font.Name = "Calibri"
        .Font.Size = 9
        .ParagraphFormat.LeftIndent = 0
        .ParagraphFormat.SpaceAfter = 6
    End With
   
    With oNewDoc.Styles(wdStyleHeader)
        .Font.Size = 8
        .ParagraphFormat.SpaceAfter = 0
    End With
    With oTable
        .Range.Style = wdStyleNormal
        .AllowAutoFit = False
        .PreferredWidthType = wdPreferredWidthPercent
        .PreferredWidth = 100
        .Columns.PreferredWidthType = wdPreferredWidthPercent
        .Columns(1).PreferredWidth = 5
        .Columns(2).PreferredWidth = 10
        .Columns(3).PreferredWidth = 25
        .Columns(4).PreferredWidth = 25
        .Columns(5).PreferredWidth = 15
        .Columns(6).PreferredWidth = 30
        .Columns(7).PreferredWidth = 2
        .Rows(1).HeadingFormat = True
    End With
    With oTable.Rows(1)
        .Range.Font.Bold = True
        .Cells(1).Range.Text = "Page"
        .Cells(2).Range.Text = "Type"
        .Cells(3).Range.Text = "Comment"
        .Cells(4).Range.Text = "Relevant text"
        .Cells(5).Range.Text = "Commenter"
        .Cells(6).Range.Text = "Action/response"
        .Cells(7).Range.Text = "Sort"
    End With
Comments:
    If cmInc = False Then GoTo Tracks
    
    If cmInc = True Then
                f = 1
                With oDoc
                    For n = 1 To nCount
                        With oDoc
                            NXTA = False
                            If cmEx = True Then
                                For i = LBound(Cmt2exArr) To UBound(Cmt2exArr)
                                    If oDoc.Comments(n).Author = Cmt2exArr(i) Then NXTA = True
                                Next
                            End If
                        End With
                            
                            If NXTA = False Then
                            
                                f = f + 1
                                
                                With oNewDoc
                                    oTable.Rows.Add
                                
                                    With oTable.Rows(f)
                                        .Cells(1).Range.Text = _
                                            oDoc.Comments(n).Scope.Information(wdActiveEndPageNumber)
                                        .Cells(2).Range.Text = "Comment"
                                        .Cells(3).Range.Text = oDoc.Comments(n).Range.Text
                                        .Cells(4).Range.Text = oDoc.Comments(n).Scope
                                        .Cells(5).Range.Text = oDoc.Comments(n).Author
                                        .Cells(7).Range.Text = oDoc.Comments(n).Scope.Information(wdFirstCharacterLineNumber)
                                    End With
                                End With
                            End If
NextComB:
                    Next
                End With
    End If
Tracks:
    If revInc = False Then GoTo Finalise
    
    Application.ScreenUpdating = False
    Selection.HomeKey Unit:=wdStory
    
    If (cmInc = False) Or (comSkip = True) Then f = 1
        
            With oDoc
                Selection.HomeKey Unit:=wdStory
                On Error GoTo NextRevb
                For rvb = 1 To rCount
                        With Selection.NextRevision
                            NXTR = False
                            If revEx = True Then
                                For j = LBound(Rev2exArr) To UBound(Rev2exArr)
                                    If .Author = Rev2exArr(j) Then NXTR = True
                                Next
                            End If
                            
                            If NXTR = False Then
                                f = f + 1
                                If (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") _
                                    And (.Type = wdRevisionDelete) Then
                                    
                                    Rvtype = "Delete"
                                    Rvpage = .Range.Information(wdActiveEndPageNumber)
                                    Rvauth = .Author
                                    Rvsort = .Range.Information(wdFirstCharacterLineNumber)
                                    Rvtext = """" & .Range.Text & """"
                                
                                ElseIf (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") _
                                    And (.Type = wdRevisionInsert) Then
                                    
                                    Rvtype = "Insert"
                                    Rvpage = .Range.Information(wdActiveEndPageNumber)
                                    Rvauth = .Author
                                    Rvsort = .Range.Information(wdFirstCharacterLineNumber)
                                    Rvtext = """" & .Range.Text & """"
                                
                                Else
                                    
                                    Rvtype = ""
                                    Rvpage = ""
                                    Rvauth = ""
                                    Rvsort = ""
                                    Rvtext = ""
                                
                                End If
                            End If
                        
                        End With
                                        
                        If NXTR = False Then
                            With oNewDoc
                                oTable.Rows.Add
                                    
                                With oTable.Rows(f)
                                    .Cells(1).Range.Text = Rvsort
                                    .Cells(2).Range.Text = Rvtype
                                    .Cells(4).Range.Text = Rvtext
                                    .Cells(5).Range.Text = Rvauth
                                    .Cells(7).Range.Text = Rvsort
                                    
                                    If Rvtype = "Delete" Then
                                        .Cells(2).Range.Font.Color = wdColorRed
                                        .Cells(4).Range.Font.Color = wdColorRed
                                    ElseIf Rvtype = "Insert" = True Then
                                        .Cells(2).Range.Font.Color = wdColorBlue
                                        .Cells(4).Range.Font.Color = wdColorBlue
                                    End If
                                End With
                            End With
                        End If
NextRevb:
                oDoc.Activate
                Next
            End With
            
            crsRng.Select
            ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
            GoTo Finalise
  
Finalise:
    oNewDoc.Activate
    Set myTable = ActiveDocument.Tables(1)
    With myTable.Borders
        .InsideLineStyle = wdLineStyleSingle
        .OutsideLineStyle = wdLineStyleSingle
    End With
    
    ActiveDocument.Tables(1).Select
    
    Selection.Sort ExcludeHeader:=True, FieldNumber:="Column 1", SortFieldType _
        :=wdSortFieldNumeric, SortOrder:=wdSortOrderAscending, FieldNumber2:= _
        "Column 7", SortFieldType2:=wdSortFieldNumeric, SortOrder2:= _
        wdSortOrderAscending, FieldNumber3:="", SortFieldType3:= _
        wdSortFieldAlphanumeric, SortOrder3:=wdSortOrderAscending, Separator:= _
        wdSortSeparateByCommas, SortColumn:=False, CaseSensitive:=False, _
        LanguageID:=wdEnglishUK, SubFieldNumber:="Paragraphs", SubFieldNumber2:= _
        "Paragraphs", SubFieldNumber3:="Paragraphs"
        
    Selection.Columns(7).Delete
    
    With ActiveDocument.Tables(1)
        noCol = .Range.Rows(1).Cells.Count
            For blRows = .Rows.Count To 1 Step -1
                With .Rows(blRows)
                    If Len(.Range) = noCol * 2 + 2 Then .Delete
                End With
            Next blRows
    End With
    Application.ScreenUpdating = True
    Application.Screenrefresh
          
    oNewDoc.Activate
    MsgBox cmSummary & revSummary & "Finished creating tracker.", vbOKOnly + vbInformation, "Job summary"
    
ExitHere:
    Set oDoc = Nothing
    Set oNewDoc = Nothing
    Set oTable = Nothing
    Set crsRng = Nothing
    Set Cmt2ex = Nothing
    Set Review2ex = Nothing
    Erase Cmt2exArr
    Erase Rev2exArr
   
End Sub
gmaxey
07-11-2018, 07:41 AM
I haven't studied you code in detail but a few quick comments.  You have a few variables that are not declared:
blDimensioned, Title, Rvtext, myTable noCol
In your public declarations, when you declare thing like this:
Public cmSummary, revSummary, scrllPs As String
You have declarded scrllP as string and everything else as a variant.  Do it like this:
Public cmSummary as String, revSummary as String, scrllPs As String
If only have one comment you get a run time error subscript out of range on this line:
        Rev2exArr(LBound(Rev2exArr)) = "ZilchRev 1"
If you have one comment and one revision, you get a run time error subscript out of range on this line:
            Cmt2exArr(LBound(Cmt2exArr)) = "ZilchCom 1"
h2whoa
07-11-2018, 07:49 AM
Thank you for putting in the time to study this code! I was too vigorous in cleaning up all the 'dead' declarations that arose during the evolution of this code, and must have wiped out some needed variables.
That's really good to know about only declaring the last item as the variable type. I was under the misapprehension that it was declaring that whole line as a string! Great to know, and may explain some errors I encountered.
I was so busy testing this code on a document with 122 tracked changes and 147 comments from 8 authors that I never thought to check with a single author. D'oh! I think I know why that is. I haven't setup the Cmt/Rev2exArr's properly. Will take a look now, revise the code and repost.
Your expertise and knowledge is genuinely appreciated. I love learning this stuff, but I only do it through brute force trial and error.
h2whoa
07-11-2018, 10:19 AM
Thanks, Greg, for pointing out some of the existing errors. I think I've corrected them. The only thing I do find is that sometimes it will fall over on the Like test or the .Type part of the Grid maker macro. However, if I close and reopen the document I was testing, it then works fine. So I don't really know why it's doing it. But overall, this seems to be doing the job now
'Public declarations
Public blDimensioned As Boolean, cmInc As Boolean, cmEx As Boolean, comSkip As Boolean, revInc As Boolean, revEx As Boolean, revSkip As Boolean
Public cmSummary As String, revSummary As String, scrllPs As String
Public nCount As Long, lAn As Long, lFAn As Long, cmTally As Long, _
        rCount As Long, indelCount As Long, lRn As Long, lFRevn As Long, revTally As Long
Public crsRng As Range
Public nc2 As Integer, rev2exN As Integer
Public Cmt2ex As New Collection, cd
Public Review2ex As New Collection, rd
Public Cmt2exArr() As String
Public Rev2exArr() As String
Public oDoc As Document
'Master sub to run the lot
Public Sub Comment_And_InDel_Grid()
i_Reset_Pub_Decs
ii_Com_Analyse
iii_Rev_Analyse
iv_Grid_maker
End Sub
'Sub to ensure all public declarations are reset
Public Sub i_Reset_Pub_Decs()
    cmInc = False: cmEx = False: comSkip = False: revInc = False: revEx = False: revSkip = False: blDimensioned = False
    
    cmSummary = "": revSummary = "": scrllPs = ""
    nCount = 0: lAn = 0: lFAn = 0: cmTally = 0: rCount = 0: indelCount = 0: lRn = 0: lFRevn = 0: revTally = 0: nc2 = 0: rev2exN = 0
    
    Set crsRng = Nothing: Set Cmt2ex = Nothing: Set Review2ex = Nothing: Set oDoc = Nothing
    Set crsRng = Nothing: Set Cmt2ex = Nothing: Set Review2ex = Nothing
    Erase Cmt2exArr: Erase Rev2exArr
End Sub
'Sub to gather comment info
Public Sub ii_Com_Analyse()
    Dim b As Long, c As Long, e As Long, g As Long, h As Long, i As Long, j As Long
    Dim sCmAuTxt1 As String, initCSum As String, chsEx As String, stCmtAuth As String, sTCmAs As String, ComNum As String, _
        rtrn2ex As String, rtrn2exsel As String, cmtMax As String, selComs As String, stSkpRv As String, C2X As String
    Dim CmtAuArr() As String
    Dim CmtCol As New Collection, ca
    sCmAuTxt1 = "The following people have made comments:" & vbNewLine & vbNewLine
    Set oDoc = ActiveDocument
    nCount = ActiveDocument.Comments.Count
    rCount = ActiveDocument.Revisions.Count
    cmInc = False
    comSkip = False
    Set crsRng = Selection.Range
    scrllPs = ActiveWindow.ActivePane.VerticalPercentScrolled
    
    If (nCount = 0) And (rCount > 0) Then
        MsgBox "There are no comments in this document.", vbOKOnly + vbCritical
        cmInc = False: cmEx = False: comSkip = True
        ReDim Cmt2exArr(0 To 1) As String
            Cmt2exArr(0) = ""
            Cmt2exArr(1) = "ZilchCom"
        GoTo Revcheck
    ElseIf (nCount = 0) And (rCount = 0) Then
        MsgBox "There are no comments or changes in this document in this document.", vbOKOnly + vbCritical
        Set oDoc = Nothing
        End
    ElseIf nCount >= 1 Then
        'Compiles a list of people who have made comments in the document
        blDimensioned = False
        For b = 1 To nCount
            stCmtAuth = ActiveDocument.Comments(b).Author
            If stCmtAuth <> "" Then
                If blDimensioned = True Then
                    ReDim Preserve CmtAuArr(0 To UBound(CmtAuArr) + 1) As String
                Else
                    ReDim CmtAuArr(0 To 0) As String
                    CmtAuArr(0) = ""
                    blDimensioned = True
                End If
                CmtAuArr(UBound(CmtAuArr)) = stCmtAuth
            End If
        Next
        
        'Collects and counts authors
        On Error Resume Next
        For Each ca In CmtAuArr
            CmtCol.Add ca, ca
        Next
        
        lAn = CmtCol.Count
        
        'Commenter exclusion text building
        If CmtCol.Count = 1 Then
            If nCount = 1 Then
                ComNum = "There is only one comment from: "
            ElseIf nCount > 1 Then
                ComNum = "There are " & nCount & " comments from: "
            End If
            cmtMax = "As there is only one author, you can't exclude them from the tracker."
            initCSum = ComNum & CmtCol(1) & "." & vbNewLine & vbNewLine & "Do you want to include comments in the tracker?"
        ElseIf CmtCol.Count >= 2 Then
            sTCmAs = ""
            For c = 1 To lAn
                sTCmAs = sTCmAs & c & ". " & CmtCol(c) & vbNewLine
            Next
            
            initCSum = "There are " & nCount & " comments from " & lAn & " people." & vbNewLine & sCmAuTxt1 & sTCmAs & vbNewLine _
            & vbNewLine & "Do you want to include comments in the tracker?"
            
            If CmtCol.Count > 2 Then
                lFAn = CmtCol.Count - 1
                cmtMax = "You can exclude comments from a maximum of " & lFAn & " people." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
            ElseIf CmtCol.Count = 2 Then
                lFAn = 1
                cmtMax = "You can exclude comments from a maximum of one person." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
            End If
        End If
    End If
    
    'Decide whether to include comments in the tracker
    selComs = MsgBox(initCSum, vbYesNo + vbQuestion)
    
    If selComs = vbYes Then
        cmInc = True
    ElseIf selComs = vbNo Then
        comSkip = True: cmInc = False: cmEx = False
        ReDim Cmt2exArr(0 To 1) As String
            Cmt2exArr(0) = ""
            Cmt2exArr(1) = "ZilchCom"
        GoTo Revcheck
    End If
Revcheck:
    If rCount > 0 Then
        stSkpRv = MsgBox("Will you want to process tracked changes?", vbYesNo + vbQuestion)
        If stSkpRv = vbYes Then
            revSkip = False: revInc = True
        ElseIf stSkpRv = vbNo Then
            revSkip = True
            revInc = False: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
        End If
        If comSkip = True Then GoTo EndComCount
    ElseIf rCount = 0 Then
        MsgBox "There are no tracked changes in this document. Only comments will be extracted.", vbOKOnly + vbInformation
        revSkip = True
        revInc = False: revEx = False
        ReDim Rev2exArr(0 To 1) As String
            Rev2exArr(0) = ""
            Rev2exArr(1) = "ZilchRev"
    End If
        
    If lAn = 1 Then
        If MsgBox(cmtMax & vbNewLine & vbNewLine & "Press OK to continue" & vbNewLine & vbNewLine & _
                "Press Cancel to quit extracting comments", vbOKCancel + vbInformation) = vbOK Then
            cmInc = True: cmEx = False
            ReDim Cmt2exArr(0 To 1) As String
                Cmt2exArr(0) = ""
                Cmt2exArr(1) = "ZilchCom"
            If nCount = 1 Then
                cmSummary = "The comment from " & """" & CmtCol(1) & """" & " has been extracted." & vbNewLine & vbNewLine
            ElseIf nCount >= 2 Then
                cmSummary = "All " & nCount & " comments from " & """" & CmtCol(1) & """" & " have been extracted." & vbNewLine & vbNewLine
            End If
            GoTo EndComCount
        Else
            cmInc = False: cmEx = False
            ReDim Cmt2exArr(0 To 1) As String
                Cmt2exArr(0) = ""
                Cmt2exArr(1) = "ZilchCom"
            GoTo EndComCount
        End If
    Else
        'Choose whether to exclude any commenters
        chsEx = MsgBox("LAN > 1!!" & sCmAuTxt1 & sTCmAs & vbNewLine & cmtMax, vbYesNoCancel)
        If chsEx = vbYes Then
            cmEx = True
n2ex:
            'Choose number of commenters to exclude
            nc2 = InputBox(sCmAuTxt1 & sTCmAs & vbNewLine & "How many people do you want to exclude?" & vbNewLine & vbNewLine & "Maximum of " & lFAn & ".", "Number to exclude")
            
            'Number validity testing
            If (IsNumeric(nc2) = False) Or (nc2 > (CmtCol.Count - 1)) Or (nc2 = 0) Then
                rtrn2ex = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract comments" _
                & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                If rtrn2ex = vbRetry Then
                    GoTo n2ex
                
                ElseIf rtrn2ex = vbAbort Then
                    cmInc = False: cmEx = False
                    ReDim Cmt2exArr(0 To 1) As String
                        Cmt2exArr(0) = ""
                        Cmt2exArr(1) = "ZilchCom"
                    GoTo EndComCount
                
                ElseIf rtrn2ex = vbIgnore Then
                    cmInc = True: cmEx = False
                    ReDim Cmt2exArr(0 To 1) As String
                        Cmt2exArr(0) = ""
                        Cmt2exArr(1) = "ZilchCom"
                    cmSummary = "All " & nCount & " comments extracted."
                    GoTo EndComCount
                End If
            Else
                'Build user-defined list of commenters to exclude
                blDimensioned = False
                For e = 1 To nc2
Exn:
                    j = InputBox(sCmAuTxt1 & sTCmAs & vbNewLine & "Enter the number of the person to exclude, from the list above.")
                        If (j > CmtCol.Count) Or (j = 0) Or (IsNumeric(j) = False) Then
                            rtrn2exsel = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract comments" _
                                        & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                                        & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                                        
                                        If rtrn2exsel = vbRetry Then
                                        GoTo Exn
                                        
                                        ElseIf rtrn2exsel = vbAbort Then
                                            cmInc = False: cmEx = False
                                            ReDim Cmt2exArr(0 To 1) As String
                                                Cmt2exArr(0) = ""
                                                Cmt2exArr(1) = "ZilchCom"
                                            GoTo EndComCount
                                        
                                        ElseIf rtrn2exsel = vbIgnore Then
                                            cmInc = True: cmEx = False
                                            ReDim Cmt2exArr(0 To 1) As String
                                                Cmt2exArr(0) = ""
                                                Cmt2exArr(1) = "ZilchCom"
                                            cmSummary = "All " & nCount & " comments extracted."
                                            GoTo EndComCount
                                        End If
                            Else
                            
                                C2X = CmtCol(j)
                                
                    
                                If blDimensioned = True Then
                                    ReDim Preserve Cmt2exArr(0 To UBound(Cmt2exArr) + 1) As String
                                Else
                                    ReDim Cmt2exArr(0 To 0) As String
                                    Cmt2exArr(0) = ""
                                    blDimensioned = True
                                End If
                                Cmt2exArr(UBound(Cmt2exArr)) = C2X
                            End If
                Next
                
                
                On Error Resume Next
                For Each cd In Cmt2exArr
                    Cmt2ex.Add cd, cd
                Next
                
                'Counts number of comments made by authors to exclude
                For g = LBound(Cmt2exArr) To UBound(Cmt2exArr)
                    h = 0
                    For i = 1 To nCount
                        With oDoc.Comments(i)
                            If .Author = Cmt2exArr(g) Then h = h + 1
                        End With
                    Next
                Next
                
                'Counts number of comments that are included in the tracker
                cmTally = nCount - h
                
                cmSummary = "Extracted:" & vbTab & vbTab & vbTab & cmTally & " comments from " & Cmt2ex.Count & " people." & vbNewLine _
                            & "Total in document:" & vbTab & vbTab & nCount & " comments from" & vbNewLine _
                            & vbTab & vbTab & vbTab & lAn & " people." & vbNewLine & vbNewLine
            
            End If
        
        ElseIf chsEx = vbNo Then
            cmInc = True: cmEx = False
            ReDim Cmt2exArr(0 To 1) As String
                Cmt2exArr(0) = ""
                Cmt2exArr(1) = "ZilchCom"
            cmSummary = "All " & nCount & " comments from " & CmtCol(1) & " extracted."
            GoTo EndComCount
        ElseIf chsEx = vbCancel Then
            cmInc = False: cmEx = False
            ReDim Cmt2exArr(0 To 1) As String
                Cmt2exArr(0) = ""
                Cmt2exArr(1) = "ZilchCom"
            GoTo EndComCount
        End If
    End If
EndComCount:
End Sub
'Sub to gather information about the tracked insertions and deletions
Public Sub iii_Rev_Analyse()
    Dim b As Long, c As Long, e As Long, g As Long, h As Long, i As Long, n As Long
    Dim sReviewerTxt1 As String, initRevSum As String, chsRevEx As String, stReviewer As String, sTReviewrs As String, _
        rtrn2Revex As String, revMax As String, selRevs As String, rtrnrvlist As String, R2X As String, RevNum As String
    Dim ReviewerArr() As String
    Dim RevCol As New Collection, ra
    If revSkip = True Then GoTo EndRevCount
    
    sReviewerTxt1 = "The following people have made tracked insertions/deletions:" & vbNewLine & vbNewLine
    revInc = False
    
    If rCount = 1 Then
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        Selection.NextRevision.Range.Select
        With Selection.Range.Revisions(1)
            If .Type = wdRevisionDelete Or wdRevisionInsert Then
                indelCount = 1
                lRn = 1
                revEx = False
                stReviewer = .Author
                ReDim ReviewerArr(0 To 1) As String
                    ReviewerArr(0) = ""
                    ReviewerArr(1) = stReviewer
                
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
            Else
                crsRng.Select
                ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
                Application.ScreenUpdating = True
                MsgBox "There are no tracked insertions/deletions in this document.", vbOKOnly + vbCritical
                revInc = False: revEx = False
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
                GoTo EndRevCount
            End If
        End With
    
    ElseIf rCount > 1 Then
        'Compiles a list of people who have made changes in the document
        
        MsgBox "Note: Word may appear to freeze at various points. Please be patient." & vbNewLine & vbNewLine & _
                "The more tracked changes there are, the longer the freezes will be.", vbOKOnly + vbInformation, "Word is now processing tracked changes"
        
        Application.Screenrefresh
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        
        indelCount = 0
        
        blDimensioned = False
        For b = 1 To rCount
            Selection.NextRevision
            With Selection.Range.Revisions(1)
                If ((.Type = wdRevisionDelete) Or (.Type = wdRevisionInsert)) _
                And (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") Then
                    indelCount = indelCount + 1
                    stReviewer = .Author
                    If stReviewer <> "" Then
                        If blDimensioned = True Then
                            ReDim Preserve ReviewerArr(0 To UBound(ReviewerArr) + 1) As String
                        Else
                            ReDim ReviewerArr(0 To 0) As String
                            ReviewerArr(0) = ""
                            blDimensioned = True
                        End If
                        ReviewerArr(UBound(ReviewerArr)) = stReviewer
                    End If
                End If
            End With
        Next
    End If
        
    'Collects and counts reviewers
    On Error Resume Next
    For Each ra In ReviewerArr
        RevCol.Add ra, ra
    Next
    
    lRn = RevCol.Count
    
    crsRng.Select
    ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
    Application.ScreenUpdating = True
    
    If indelCount = 0 Then
        MsgBox "There are no tracked insertions/deletions in this document.", vbOKOnly + vbCritical
        revInc = False
        GoTo EndRevCount
    End If
    
    'Reviewer exclusion text building
    If RevCol.Count = 1 Then
        If indelCount = 1 Then
            RevNum = "There is only one tracked insertion/deletion from: "
        ElseIf indelCount > 1 Then
            RevNum = "There are " & indelCount & " tracked insertions/deletions from: "
        End If
        revMax = "There is only one reviewer, so you can't exclude them from the tracker."
        initRevSum = RevNum & RevCol(1) & "." & vbNewLine & vbNewLine & "Do you want to include tracked changes in the tracker?"
    ElseIf RevCol.Count > 1 Then
        sTReviewrs = ""
        For c = 1 To lRn
            sTReviewrs = sTReviewrs & c & ". " & RevCol(c) & vbNewLine
        Next
        
        initRevSum = "There are " & indelCount & " tracked insertions/deletions from " & lRn & " people." & vbNewLine & sReviewerTxt1 & sTReviewrs & vbNewLine _
        & vbNewLine & "Do you want to include tracked changes in the tracker?"
        
        If RevCol.Count > 2 Then
            lFRevn = RevCol.Count - 1
            revMax = "You can exclude tracked insertions/deletions from a maximum of " & lFRevn & " people." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
        ElseIf RevCol.Count = 2 Then
            lFRevn = 1
            revMax = "You can exclude tracked insertions/deletions from a maximum of one person." & vbNewLine & vbNewLine & "Do you want to exclude anyone?"
        End If
    End If
    
    'Decide whether to include tracked changes in the tracker
    selRevs = MsgBox(initRevSum, vbYesNo + vbQuestion)
    
    If selRevs = vbYes Then
        revInc = True
    ElseIf selRevs = vbNo Then
        revInc = False: revEx = False
        ReDim Rev2exArr(0 To 1) As String
            Rev2exArr(0) = ""
            Rev2exArr(1) = "ZilchRev"
        GoTo EndRevCount
    End If
        
    If lRn = 1 Then
        If MsgBox(revMax, vbOKCancel + vbInformation) = vbOK Then
            revInc = True: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            If indelCount = 1 Then
                revSummary = "The tracked insertions/deletion from " & """" & RevCol(1) & """" & " has been extracted." & vbNewLine & vbNewLine
            ElseIf indelCount >= 2 Then
                revSummary = "All " & indelCount & " tracked insertions/deletions from " & """" & RevCol(1) & """" & " have been extracted." & vbNewLine & vbNewLine
            End If
            GoTo EndRevCount
        Else
            revInc = False: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            GoTo EndRevCount
        End If
    Else
        'Choose whether to exclude any reviewers
        chsRevEx = MsgBox(sReviewerTxt1 & sTReviewrs & vbNewLine & revMax, vbYesNoCancel)
        If chsRevEx = vbYes Then
            revEx = True
nrv2ex:
            'Choose number of reviewers to exclude
            rev2exN = InputBox(sReviewerTxt1 & sTReviewrs & vbNewLine & "How many people do you want to exclude?" & vbNewLine & vbNewLine & "Maximum of " & lFRevn & ".", "Number to exclude")
            
            'Number validity testing
            If (IsNumeric(rev2exN) = False) Or (rev2exN > (RevCol.Count - 1)) Or (rev2exN < 1) Then
                rtrn2Revex = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract revisions" _
                & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                If rtrn2Revex = vbRetry Then
                    GoTo nrv2ex
                ElseIf rtrn2Revex = vbAbort Then
                    revInc = False: revEx = False
                    ReDim Rev2exArr(0 To 1) As String
                        Rev2exArr(0) = ""
                        Rev2exArr(1) = "ZilchRev"
                    GoTo EndRevCount
                ElseIf rtrn2Revex = vbIgnore Then
                    revInc = True: revEx = False
                    ReDim Rev2exArr(0 To 1) As String
                        Rev2exArr(0) = ""
                        Rev2exArr(1) = "ZilchRev"
                    revSummary = "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted."
                    GoTo EndRevCount
                End If
            Else
                'Build user-defined list of reviewers to exclude
                blDimensioned = False
                For e = 1 To rev2exN
Revexlist:
                    n = InputBox(sReviewerTxt1 & sTReviewrs & vbNewLine & "Enter the number of the person to exclude, exactly " & _
                                vbNewLine & "as it appears in the list above.")
                        If (n > RevCol.Count) Or (n = 0) Or (IsNumeric(n) = False) Then
                            rtrnrvlist = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract revisions" _
                                        & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                                        & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                                        
                                        If rtrn2Revex = vbRetry Then
                                            GoTo Revexlist
                                        ElseIf rtrn2Revex = vbAbort Then
                                            revInc = False: revEx = False
                                            ReDim Rev2exArr(0 To 1) As String
                                                Rev2exArr(0) = ""
                                                Rev2exArr(1) = "ZilchRev"
                                            GoTo EndRevCount
                                        ElseIf rtrn2Revex = vbIgnore Then
                                            revInc = True: revEx = False
                                            ReDim Rev2exArr(0 To 1) As String
                                                Rev2exArr(0) = ""
                                                Rev2exArr(1) = "ZilchRev"
                                            revSummary = "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted."
                                            GoTo EndRevCount
                                        End If
                        Else
                            R2X = RevCol(n)
                            
                            If blDimensioned = True Then
                                ReDim Preserve Rev2exArr(0 To UBound(Rev2exArr) + 1) As String
                            Else
                                ReDim Rev2exArr(0 To 0) As String
                                Rev2exArr(0) = ""
                                blDimensioned = True
                            End If
                            Rev2exArr(UBound(Rev2exArr)) = R2X
                        End If
                Next
                
                On Error Resume Next
                For Each rd In Rev2exArr
                    Review2ex.Add rd, rd
                Next
                
                
                'Counts number of changes made by reviewers to exclude
                Application.ScreenUpdating = False
                Selection.HomeKey Unit:=wdStory
                
                
                h = 0
                For i = 1 To rCount
                    With Selection.NextRevision
                        If .Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*" Then
                            For g = LBound(Rev2exArr) To UBound(Rev2exArr)
                                If .Author = Rev2exArr(g) Then h = h + 1
                            Next
                        End If
                    End With
                Next
                
                
                crsRng.Select
                ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
                Application.ScreenUpdating = True
                Application.Screenrefresh
                
                
                'Counts number of changes that are included in the tracker
                revTally = indelCount - h
                
                revSummary = "Extracted:" & vbTab & vbTab & vbTab & revTally & " tracked insertions/deletions" & vbNewLine _
                            & vbTab & vbTab & vbTab & "from " & Review2ex.Count & " people." & vbNewLine & "Total in document:" _
                            & vbTab & vbTab & indelCount & " tracked insertions/deletions" & vbNewLine _
                            & vbTab & vbTab & vbTab & "from " & lRn & " people." & vbNewLine & vbNewLine
            
            End If
            
        ElseIf chsRevEx = vbNo Then
            revInc = True: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            revSummary = "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted."
            GoTo EndRevCount
        ElseIf chsRevEx = vbCancel Then
            revInc = False: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            GoTo EndRevCount
        End If
    End If
EndRevCount:
End Sub
'Final sub to collect everything together and put it into the grid
Public Sub iv_Grid_maker()
    Dim oNewDoc As Document
    Dim oTable As Table, oTracker As Table
    Dim NXTA As Boolean, NXTR As Boolean
    Dim f As Long, i As Long, j As Long, n As Long, z As Long, blRows As Long
    Dim Rvtype As String, Rvpage As String, Rvsort As String, Rvauth As String, Rvtext As String
    
    Set oDoc = ActiveDocument
    rCount = oDoc.Revisions.Count
    
    Application.Screenrefresh
    
    If cmInc = False And revInc = False Then
        MsgBox "No comments or revisions selected.", vbOKOnly + vbInformation
        GoTo ExitHere
    End If
    
       
Start:
    Application.Screenrefresh
    MsgBox "Word may appear to freeze during this process!" & vbNewLine & vbNewLine & "Don't panic! Word has not crashed. Just wait for the process to finish." & vbNewLine & vbNewLine & "The more revisions and comments there are, the longer the process will take.", vbOKOnly, "DON'T PANIC!"
    Application.ScreenUpdating = False
    Set oNewDoc = Documents.Add
    oNewDoc.PageSetup.Orientation = wdOrientLandscape
    With oNewDoc
        .Content = ""
        If cmInc = True And revInc = False Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=nCount + 1, _
                NumColumns:=7)
                
            .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Comments extracted from: " & oDoc.Name
            
        ElseIf cmInc = False And revInc = True Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=rCount + 1, _
                NumColumns:=7)
                
            .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Revisions extracted from: " & oDoc.Name
                
        ElseIf cmInc = True And revInc = True Then
            Set oTable = .Tables.Add _
                (Range:=Selection.Range, _
                numRows:=nCount + rCount + 1, _
                NumColumns:=7)
                
            .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = _
            "Comments and revisions extracted from: " & oDoc.Name
                
        End If
    End With
    With oNewDoc.Styles(wdStyleNormal)
        .Font.Name = "Calibri"
        .Font.Size = 9
        .ParagraphFormat.LeftIndent = 0
        .ParagraphFormat.SpaceAfter = 6
    End With
   
    With oNewDoc.Styles(wdStyleHeader)
        .Font.Size = 8
        .ParagraphFormat.SpaceAfter = 0
    End With
    With oTable
        .Range.Style = wdStyleNormal
        .AllowAutoFit = False
        .PreferredWidthType = wdPreferredWidthPercent
        .PreferredWidth = 100
        .Columns.PreferredWidthType = wdPreferredWidthPercent
        .Columns(1).PreferredWidth = 5
        .Columns(2).PreferredWidth = 10
        .Columns(3).PreferredWidth = 25
        .Columns(4).PreferredWidth = 25
        .Columns(5).PreferredWidth = 15
        .Columns(6).PreferredWidth = 30
        .Columns(7).PreferredWidth = 2
        .Rows(1).HeadingFormat = True
    End With
    With oTable.Rows(1)
        .Range.Font.Bold = True
        .Cells(1).Range.Text = "Page"
        .Cells(2).Range.Text = "Type"
        .Cells(3).Range.Text = "Comment"
        .Cells(4).Range.Text = "Relevant text"
        .Cells(5).Range.Text = "Commenter"
        .Cells(6).Range.Text = "Action/response"
        .Cells(7).Range.Text = "Sort"
    End With
Comments:
    If cmInc = False Then GoTo Tracks
    
    If cmInc = True Then
                f = 1
                With oDoc
                    For n = 1 To nCount
                        With oDoc
                            NXTA = False
                            If cmEx = True Then
                                For i = LBound(Cmt2exArr) To UBound(Cmt2exArr)
                                    If oDoc.Comments(n).Author = Cmt2exArr(i) Then NXTA = True
                                Next
                            End If
                        End With
                            
                            If NXTA = False Then
                            
                                f = f + 1
                                
                                With oNewDoc
                                    oTable.Rows.Add
                                
                                    With oTable.Rows(f)
                                        .Cells(1).Range.Text = _
                                            oDoc.Comments(n).Scope.Information(wdActiveEndPageNumber)
                                        .Cells(2).Range.Text = "Comment"
                                        .Cells(3).Range.Text = oDoc.Comments(n).Range.Text
                                        .Cells(4).Range.Text = oDoc.Comments(n).Scope
                                        .Cells(5).Range.Text = oDoc.Comments(n).Author
                                        .Cells(7).Range.Text = oDoc.Comments(n).Scope.Information(wdFirstCharacterLineNumber)
                                    End With
                                End With
                            End If
NextComB:
                    Next
                End With
    End If
Tracks:
    If revInc = False Then GoTo Finalise
    
    Application.ScreenUpdating = False
    Selection.HomeKey Unit:=wdStory
    
    If (cmInc = False) Or (comSkip = True) Then f = 1
        
            With oDoc
                Selection.HomeKey Unit:=wdStory
                On Error GoTo NextRevb
                For z = 0 To rCount
                    With oDoc
                        With Selection.NextRevision
                            NXTR = False
                            If revEx = True Then
                                For j = LBound(Rev2exArr) To UBound(Rev2exArr)
                                    If .Author = Rev2exArr(j) Then NXTR = True
                                Next
                            End If
                            
                            If NXTR = False Then
                                f = f + 1
                                If (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") _
                                    And (.Type = wdRevisionDelete) Then
                                    
                                    Rvtype = "Delete"
                                    Rvpage = .Range.Information(wdActiveEndPageNumber)
                                    Rvauth = .Author
                                    Rvsort = .Range.Information(wdFirstCharacterLineNumber)
                                    Rvtext = """" & .Range.Text & """"
                                
                                ElseIf (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") _
                                    And (.Type = wdRevisionInsert) Then
                                    
                                    Rvtype = "Insert"
                                    Rvpage = .Range.Information(wdActiveEndPageNumber)
                                    Rvauth = .Author
                                    Rvsort = .Range.Information(wdFirstCharacterLineNumber)
                                    Rvtext = """" & .Range.Text & """"
                                
                                Else
                                    
                                    Rvtype = ""
                                    Rvpage = ""
                                    Rvauth = ""
                                    Rvsort = ""
                                    Rvtext = ""
                                
                                End If
                            End If
                        
                        End With
                    End With
                                        
                        If NXTR = False Then
                            With oNewDoc
                                oTable.Rows.Add
                                    
                                With oTable.Rows(f)
                                    .Cells(1).Range.Text = Rvpage
                                    .Cells(2).Range.Text = Rvtype
                                    .Cells(4).Range.Text = Rvtext
                                    .Cells(5).Range.Text = Rvauth
                                    .Cells(7).Range.Text = Rvsort
                                    
                                    If Rvtype = "Delete" Then
                                        .Cells(2).Range.Font.Color = wdColorRed
                                        .Cells(4).Range.Font.Color = wdColorRed
                                    ElseIf Rvtype = "Insert" = True Then
                                        .Cells(2).Range.Font.Color = wdColorBlue
                                        .Cells(4).Range.Font.Color = wdColorBlue
                                    End If
                                End With
                            End With
                        End If
NextRevb:
                oDoc.Activate
                Next
            End With
            
            crsRng.Select
            ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
            GoTo Finalise
  
Finalise:
    oNewDoc.Activate
    Set oTracker = ActiveDocument.Tables(1)
    With oTracker.Borders
        .InsideLineStyle = wdLineStyleSingle
        .OutsideLineStyle = wdLineStyleSingle
    End With
    
    oTracker.Select
    
    With Selection
        .Sort ExcludeHeader:=True, FieldNumber:="Column 1", SortFieldType _
        :=wdSortFieldNumeric, SortOrder:=wdSortOrderAscending, FieldNumber2:= _
        "Column 7", SortFieldType2:=wdSortFieldNumeric, SortOrder2:= _
        wdSortOrderAscending, FieldNumber3:="", SortFieldType3:= _
        wdSortFieldAlphanumeric, SortOrder3:=wdSortOrderAscending, Separator:= _
        wdSortSeparateByCommas, SortColumn:=False, CaseSensitive:=False, _
        LanguageID:=wdEnglishUK, SubFieldNumber:="Paragraphs", SubFieldNumber2:= _
        "Paragraphs", SubFieldNumber3:="Paragraphs"
        
        .Columns(7).Delete
    End With
    
    
    With oTracker
            For blRows = .Rows.Count To 1 Step -1
                With .Rows(blRows)
                    If (.Cells(1).Range.Text = "" & Chr(13) & Chr(7)) And (.Cells(2).Range.Text = "" & Chr(13) & Chr(7)) And (.Cells(3).Range.Text = "" & Chr(13) & Chr(7)) _
                        And (.Cells(4).Range.Text = "" & Chr(13) & Chr(7)) And (.Cells(5).Range.Text = "" & Chr(13) & Chr(7)) _
                        And (.Cells(6).Range.Text = "" & Chr(13) & Chr(7)) Then .Delete
                End With
            Next blRows
    End With
    
    Application.ScreenUpdating = True
    Application.Screenrefresh
          
    oNewDoc.Activate
    MsgBox cmSummary & revSummary & "Finished creating tracker.", vbOKOnly + vbInformation, "Job summary"
    
ExitHere:
    cmInc = False: cmEx = False: comSkip = False: revInc = False: revEx = False: revSkip = False: blDimensioned = False
    
    cmSummary = "": revSummary = "": scrllPs = ""
    nCount = 0: lAn = 0: lFAn = 0: cmTally = 0: rCount = 0: indelCount = 0: lRn = 0: lFRevn = 0: revTally = 0: nc2 = 0: rev2exN = 0
    
    Set crsRng = Nothing: Set Cmt2ex = Nothing: Set Review2ex = Nothing: Set oDoc = Nothing
    Set crsRng = Nothing: Set Cmt2ex = Nothing: Set Review2ex = Nothing
    Erase Cmt2exArr: Erase Rev2exArr
    
    Set oNewDoc = Nothing: Set oTable = Nothing: Set oTracker = Nothing
   
End Sub
gmaxey
07-11-2018, 02:09 PM
OK,  I ran your revised code with one comment, one insertion and one deletion.  
I think that there were no fewer than seven message boxes that popped up in the process.  Your user's might find that annoying.
The code error'd on this line:  If (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") _
You have not commented you code very well so I'm not sure what you are trying to do exactly but I did revise  your final macro a bit and it runs without error:
Public Sub iv_Grid_maker()
Dim oNewDoc As Document
Dim oTbl As Table
Dim NXTA As Boolean, NXTR As Boolean
Dim lngIndex As Long
Dim oRev As Revision
Dim lngRow As Long, i As Long, j As Long
Dim Rvtype As String, Rvpage As String, Rvsort As String, Rvauth As String, Rvtext As String
    
  Set oDoc = ActiveDocument
  lngRevisions = oDoc.Revisions.Count
  If cmInc = False And revInc = False Then
    MsgBox "No comments or revisions selected.", vbOKOnly + vbInformation
    GoTo lbl_Exit
  End If
  MsgBox "Word may appear to freeze during this process!" & vbNewLine & vbNewLine & "Don't panic! Word has not crashed. Just wait for the process to finish." & vbNewLine & vbNewLine & "The more revisions and comments there are, the longer the process will take.", vbOKOnly, "DON'T PANIC!"
  Application.ScreenUpdating = False
  Set oNewDoc = Documents.Add
  With oNewDoc
    .PageSetup.Orientation = wdOrientLandscape
    Select Case True
      Case cmInc And revInc
       .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = "Comments and revisions extracted from: " & oDoc.Name
      Case cmInc And Not revInc
        .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = "Comments extracted from: " & oDoc.Name
      Case revInc And Not cmInc
        .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = "Revisions extracted from: " & oDoc.Name
    End Select
    With .Styles(wdStyleNormal)
      .Font.Name = "Calibri"
      .Font.Size = 9
      .ParagraphFormat.LeftIndent = 0
      .ParagraphFormat.SpaceAfter = 6
    End With
    With .Styles(wdStyleHeader)
      .Font.Size = 8
      .ParagraphFormat.SpaceAfter = 0
    End With
    Set oTbl = .Tables.Add(Selection.Range, lngComments + lngRevisions + 1, 7)
    With oTbl
      .Range.Style = wdStyleNormal
      .AllowAutoFit = False
      .PreferredWidthType = wdPreferredWidthPercent
      .PreferredWidth = 100
      .Columns.PreferredWidthType = wdPreferredWidthPercent
      .Columns(1).PreferredWidth = 5
      .Columns(2).PreferredWidth = 10
      .Columns(3).PreferredWidth = 25
      .Columns(4).PreferredWidth = 25
      .Columns(5).PreferredWidth = 15
      .Columns(6).PreferredWidth = 30
      .Columns(7).PreferredWidth = 2
      With .Rows(1)
        .HeadingFormat = True
        .Range.Font.Bold = True
        .Cells(1).Range.Text = "Page"
        .Cells(2).Range.Text = "Type"
        .Cells(3).Range.Text = "Comment"
        .Cells(4).Range.Text = "Relevant text"
        .Cells(5).Range.Text = "Commenter"
        .Cells(6).Range.Text = "Action/response"
        .Cells(7).Range.Text = "Sort"
      End With
    End With
    If cmInc = True Then
      lngRow = 1
      For lngIndex = 1 To lngComments
        NXTA = False
        If cmEx = True Then
          For i = LBound(Cmt2exArr) To UBound(Cmt2exArr)
            If .Comments(lngIndex).Author = Cmt2exArr(i) Then NXTA = True
          Next
        End If
        If NXTA = False Then
          lngRow = lngRow + 1
          oTbl.Rows.Add
          With oTbl.Rows(lngRow)
            .Cells(1).Range.Text = oDoc.Comments(lngIndex).Scope.Information(wdActiveEndPageNumber)
            .Cells(2).Range.Text = "Comment"
            .Cells(3).Range.Text = oDoc.Comments(lngIndex).Range.Text
            .Cells(4).Range.Text = oDoc.Comments(lngIndex).Scope
            .Cells(5).Range.Text = oDoc.Comments(lngIndex).Author
            .Cells(7).Range.Text = oDoc.Comments(lngIndex).Scope.Information(wdFirstCharacterLineNumber)
           End With
        End If
      Next
    End If
    If revInc Then
      If (cmInc = False) Or (comSkip = True) Then lngRow = 1
      On Error GoTo NextRevb
      For lngIndex = 1 To lngRevisions
        Set oRev = oDoc.Revisions(lngIndex)
        With oRev
          NXTR = False
          If revEx = True Then
            For j = LBound(Rev2exArr) To UBound(Rev2exArr)
              If .Author = Rev2exArr(j) Then NXTR = True
            Next
          End If
          If NXTR = False Then
            lngRow = lngRow + 1
            If (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") And (.Type = wdRevisionDelete) Then
              Rvtype = "Delete"
              Rvpage = .Range.Information(wdActiveEndPageNumber)
              Rvauth = .Author
              Rvsort = .Range.Information(wdFirstCharacterLineNumber)
              Rvtext = """" & .Range.Text & """"
            ElseIf (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") And (.Type = wdRevisionInsert) Then
              Rvtype = "Insert"
              Rvpage = .Range.Information(wdActiveEndPageNumber)
              Rvauth = .Author
              Rvsort = .Range.Information(wdFirstCharacterLineNumber)
              Rvtext = """" & .Range.Text & """"
            Else
              Rvtype = ""
              Rvpage = ""
              Rvauth = ""
              Rvsort = ""
              Rvtext = ""
            End If
          End If
        End With
        If NXTR = False Then
          oTbl.Rows.Add
          With oTbl.Rows(lngRow)
            .Cells(1).Range.Text = Rvpage
            .Cells(2).Range.Text = Rvtype
            .Cells(4).Range.Text = Rvtext
            .Cells(5).Range.Text = Rvauth
            .Cells(7).Range.Text = Rvsort
            If Rvtype = "Delete" Then
              .Cells(2).Range.Font.Color = wdColorRed
              .Cells(4).Range.Font.Color = wdColorRed
            ElseIf Rvtype = "Insert" = True Then
              .Cells(2).Range.Font.Color = wdColorBlue
              .Cells(4).Range.Font.Color = wdColorBlue
            End If
          End With
        End If
NextRevb:
      Next
    End If
  End With
  oDoc.Activate
  crsRng.Select
  ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
Finalise:
  oNewDoc.Activate
  With oTbl.Borders ' Tracker.Borders
    .InsideLineStyle = wdLineStyleSingle
    .OutsideLineStyle = wdLineStyleSingle
  End With
  oTbl.Select
  With Selection
    .Sort ExcludeHeader:=True, FieldNumber:="Column 1", SortFieldType _
    :=wdSortFieldNumeric, SortOrder:=wdSortOrderAscending, FieldNumber2:= _
    "Column 7", SortFieldType2:=wdSortFieldNumeric, SortOrder2:= _
    wdSortOrderAscending, FieldNumber3:="", SortFieldType3:= _
    wdSortFieldAlphanumeric, SortOrder3:=wdSortOrderAscending, Separator:= _
    wdSortSeparateByCommas, SortColumn:=False, CaseSensitive:=False, _
    LanguageID:=wdEnglishUK, SubFieldNumber:="Paragraphs", SubFieldNumber2:= _
    "Paragraphs", SubFieldNumber3:="Paragraphs"
    .Columns(7).Delete
  End With
  With oTbl
    For lngIndex = .Rows.Count To 1 Step -1
      If Len(.Rows(lngIndex).Range.Text) = 14 Then .Rows(lngIndex).Delete
    Next lngIndex
  End With
  Application.ScreenUpdating = True
  Application.ScreenRefresh
  oNewDoc.Activate
  MsgBox cmSummary & revSummary & "Finished creating tracker.", vbOKOnly + vbInformation, "Job summary"
lbl_Exit:
  Set oNewDoc = Nothing: Set oTbl = Nothing: Set oRev = Nothing
End Sub
We each develop our own styles. I find it easier when my variables have meaningful names e.g., lngComments vs nCount.
h2whoa
07-11-2018, 02:39 PM
This is brilliant, thank you, Greg.
Basically, the  If (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*")  test was my clumsy way to smooth over some weird runtime errors I was getting when the code tried to read .Author and .Type properties. The errors were unpredictable so I wondered if they were caused by tracked changes in non-text ranges (i.e. pictures). So I added that to make sure only alphanumeric ranges were included. I'm not entirely sure it's necessary, but was an idea when I was at my wits' end.
Kilroy
07-13-2018, 07:12 AM
I added the new IV portion and now the comments are not populating the table.
h2whoa
07-13-2018, 07:51 AM
I added the new IV portion and now the comments are not populating the table.
Yes, there was an undeclared variable. I have actually just finished updating it. The whole macro now runs with fewer message boxes. I think the the below code should work now!
'Public declarations for variables used throughout
Public blDimensioned As Boolean, cmInc As Boolean, cmEx As Boolean, comSkip As Boolean, revInc As Boolean, revEx As Boolean, revSkip As Boolean
Public cmSummary As String, revSummary As String, scrllPs As String
Public lngComments As Long, lAn As Long, lFAn As Long, cmTally As Long, _
        lngRevisions As Long, indelCount As Long, lRn As Long, lFRevn As Long, revTally As Long
Public crsRng As Range
Public nc2 As Integer, rev2exN As Integer
Public Cmt2ex As New Collection, cd
Public Review2ex As New Collection, rd
Public Cmt2exArr() As String
Public Rev2exArr() As String
Public oDoc As Document
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Gathers information on the comments
Public Sub Comment_And_InDel_Grid()
If MsgBox("1." & vbTab & "Word may appear to freeze at multiple points" & vbNewLine & vbTab & "during this process." & vbNewLine & vbNewLine & _
        "2." & vbTab & "This is normal as this process is memory-intesive." & vbNewLine & vbTab & "Word has not crashed!" & vbNewLine & vbNewLine & _
        "3." & vbTab & "The more revisions and comments there are, the longer" & vbNewLine & vbTab & "the process will take. Just wait for the " & _
        "process to finish." & vbNewLine & vbNewLine & "4." & vbTab & "You will be asked to make choices at a couple of points" _
        & vbTab & vbTab & "in this process.", vbOKCancel + vbInformation, "Important notes") = vbCancel Then End
i_Reset_Pub_Decs
ii_Com_Analyse
iii_Rev_Analyse
iv_Grid_maker
End Sub
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Resets the public declarations
Public Sub i_Reset_Pub_Decs()
    cmInc = False: cmEx = False: comSkip = False: revInc = False: revEx = False: revSkip = False: blDimensioned = False
    
    cmSummary = "": revSummary = "": scrllPs = ""
    lngComments = 0: lAn = 0: lFAn = 0: cmTally = 0: lngRevisions = 0: indelCount = 0: lRn = 0: lFRevn = 0: revTally = 0: nc2 = 0: rev2exN = 0
    
    Set crsRng = Nothing: Set Cmt2ex = Nothing: Set Review2ex = Nothing: Set oDoc = Nothing
    Set crsRng = Nothing: Set Cmt2ex = Nothing: Set Review2ex = Nothing
    Erase Cmt2exArr: Erase Rev2exArr
End Sub
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Gathers information on the comments
Public Sub ii_Com_Analyse()
    Dim lngIndex As Long, lngIndexA As Long, lngAuthExNum As Long, lngCombSel As Long, lngInDeIndex As Long, lngComAusExt As Long
    Dim sCmAuTxt1 As String, initCSum As String, stCmtAuth As String, sTCmAs As String, ComNum As String, _
        rtrn2ex As String, rtrn2exsel As String, cmtMax As String, selComs As String, C2X As String, strComExList As String, _
        singleComSum As String, strPerPeop As String
    Dim CmtAuArr() As String
    Dim SingComBool As Boolean
    Dim CmtCol As New Collection, ca
    SingComBool = False
    sCmAuTxt1 = "The following people have made comments:" & vbNewLine & vbNewLine
    Set oDoc = ActiveDocument
    lngComments = ActiveDocument.Comments.Count
    lngRevisions = ActiveDocument.Revisions.Count
    cmInc = False
    comSkip = False
    Set crsRng = Selection.Range
    scrllPs = ActiveWindow.ActivePane.VerticalPercentScrolled
    Application.ScreenUpdating = False
    Selection.HomeKey Unit:=wdStory
    
    indelCount = 0 'indelCount counts the number of tracked insertions and deletions
    
    For lngInDeIndex = 1 To lngRevisions
        Selection.NextRevision
        With Selection.Range.Revisions(1)
            'The like test has been added here (and throughout) to prevent errors when tracked changes are not in text ranges
            If ((.Type = wdRevisionDelete) Or (.Type = wdRevisionInsert)) _
            And (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") Then indelCount = indelCount + 1
        End With
    Next
    
    crsRng.Select
    ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
    Application.ScreenUpdating = True
    Application.Screenrefresh
    'This section handles the initial options, based on number of comments/revisions
    If (lngComments = 0) And (indelCount > 0) Then
        If MsgBox("There are no comments in this document but there are " & indelCount & " tracked insertions/deletions." & vbNewLine & vbNewLine _
                    & "Do you want to proceed with extracting tracked changes?", vbYesNo + vbInformation) = vbYes Then
            
            cmInc = False: cmEx = False: comSkip = True
            ReDim Cmt2exArr(0 To 1) As String
                Cmt2exArr(0) = ""
                Cmt2exArr(1) = "ZilchCom"
            
            revSkip = False: revInc = True
            GoTo EndComCount
        Else
            MsgBox "Process terminated.", vbOKOnly + vbCritical
            Set oDoc = Nothing
            End
        End If
    ElseIf (lngComments = 0) And (lngRevisions = 0) Then
        MsgBox "There are no comments or tracked insertions/deletions in this document." & vbNewLine & vbNewLine _
                    & "Process terminated.", vbOKOnly + vbCritical
        Set oDoc = Nothing
        End
    ElseIf lngComments >= 1 Then
        'Compiles a list of people who have made comments in the document
        blDimensioned = False
        For lngIndex = 1 To lngComments
            stCmtAuth = ActiveDocument.Comments(lngIndex).Author
            If stCmtAuth <> "" Then
                If blDimensioned = True Then
                    ReDim Preserve CmtAuArr(0 To UBound(CmtAuArr) + 1) As String
                Else
                    ReDim CmtAuArr(0 To 0) As String
                    CmtAuArr(0) = ""
                    blDimensioned = True
                End If
                CmtAuArr(UBound(CmtAuArr)) = stCmtAuth
            End If
        Next
    End If
        
    'Collects and counts authors
    On Error Resume Next
    For Each ca In CmtAuArr
        CmtCol.Add ca, ca
    Next
    
    lAn = CmtCol.Count
        
    'Limits choices if there are only comments from 1 person
    If CmtCol.Count = 1 Then
        SingComBool = True
        If indelCount = 0 Then
            If lngComments = 1 Then
                ComNum = "There are no tracked insertions/deletions and" & vbNewLine & _
                            "there is only one comment from: " & CmtCol(1) & vbNewLine & vbNewLine & _
                            "Do you you still want to extract their comment?"
                            
                singleComSum = "The comment from " & """" & CmtCol(1) & """" & " has been extracted." & vbNewLine & vbNewLine
            ElseIf lngComments >= 2 Then ComNum = "There are no tracked insertions/deletions but" & vbNewLine & _
                                            "there are " & lngComments & " comments from: " & CmtCol(1) & vbNewLine & vbNewLine & _
                                            "Do you you still want to extract their comments?"
                singleComSum = "All " & lngComments & " comments from " & """" & CmtCol(1) & """" & " have been extracted." & vbNewLine & vbNewLine
            End If
            
            revSkip = True: revInc = False 'Choose whether to include comments from single author
            If MsgBox(ComNum, vbYesNo + vbQuestion) = vbYes Then
                cmInc = True: cmEx = False: comSkip = False
                ReDim Cmt2exArr(0 To 1) As String
                    Cmt2exArr(0) = ""
                    Cmt2exArr(1) = "ZilchCom"
                cmSummary = "COMMENTS:" & vbNewLine & singleComSum & vbNewLine
                GoTo EndComCount
            Else
                MsgBox "Process terminated.", vbOKOnly + vbCritical
                Set oDoc = Nothing
                End
            End If
        
        ElseIf indelCount >= 1 Then
            If lngComments = 1 Then
                initCSum = "There is only one comment from: " & CmtCol(1) & vbNewLine & vbNewLine
                GoTo CombiSelect
            ElseIf lngComments >= 2 Then
                initCSum = "There are " & lngComments & " comments from: " & CmtCol(1) & vbNewLine & vbNewLine
                GoTo CombiSelect
            End If
        End If
    'Options for more than one commenter
    ElseIf CmtCol.Count >= 2 Then
        SingComBool = False
        sTCmAs = ""
        For lngIndex = 1 To lAn
            sTCmAs = sTCmAs & lngIndex & ". " & CmtCol(lngIndex) & vbNewLine
        Next
        
        strComExList = "0. To exclude nobody" & vbNewLine & sTCmAs
        
        initCSum = "There are " & lngComments & " comments from " & lAn & " people." & vbNewLine & sCmAuTxt1 & sTCmAs & vbNewLine
        
        If CmtCol.Count > 2 Then
            lFAn = CmtCol.Count - 1
            cmtMax = "You can exclude comments from a maximum of " & lFAn & " people." & vbNewLine & vbNewLine
        ElseIf CmtCol.Count = 2 Then
            lFAn = 1
            cmtMax = "You can exclude comments from a maximum of one person." & vbNewLine & vbNewLine
        End If
        
        If indelCount = 0 Then
            selComs = MsgBox("There are no insertions/deletions in this document." & vbNewLine & vbNewLine & _
                        initCSum & "Do you want to continue with just extracting comments?", vbYesNo + vbQuestion)
            If selComs = vbYes Then
                cmInc = True: revSkip = True: revInc = False: revEx = False
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
                GoTo n2ex
            ElseIf selComs = vbNo Then
                MsgBox "Process terminated.", vbOKOnly + vbCritical
                    Set oDoc = Nothing
                    End
            End If
        ElseIf indelCount >= 1 Then
            GoTo CombiSelect
        End If
    End If
    
'This section is to choose whether to extract just comments, revisions or both
CombiSelect:
    lngCombSel = InputBox(initCSum & "There are also " & indelCount & " tracked insertions/deletions that could be extracted." _
                    & vbNewLine & vbNewLine & "In the box below, type a number corresponding to your choice." _
                    & vbNewLine & vbNewLine & "1: " & "To ONLY extract comments." & vbNewLine & _
                    "2: " & "To ONLY extract revisions." & vbNewLine & "3: " & "To extract comments and revisions." & vbNewLine & _
                    "4: " & "To cancel and exit.")
    If (IsNumeric(lngCombSel) = False) Or (lngCombSel < 1) Or (lngCombSel > 4) Then
        MsgBox "Invalid option selected. Please try again.", vbOKOnly + vbCritical
        GoTo CombiSelect
    ElseIf lngCombSel = 1 Then
        cmInc = True: comSkip = False: revSkip = True: revInc = False: revEx = False
        ReDim Rev2exArr(0 To 1) As String
            Rev2exArr(0) = ""
            Rev2exArr(1) = "ZilchRev"
    ElseIf lngCombSel = 2 Then
        cmInc = False: cmEx = False: comSkip = True
        ReDim Cmt2exArr(0 To 1) As String
            Cmt2exArr(0) = ""
            Cmt2exArr(1) = "ZilchCom"
        revSkip = False: revInc = True
        cmSummary = ""
        GoTo EndComCount
    ElseIf lngCombSel = 3 Then
        cmInc = True: comSkip = False: revInc = True: revSkip = False
    ElseIf lngCombSel = 4 Then
        MsgBox "Process terminated.", vbOKOnly + vbCritical
        Set oDoc = Nothing
        End
    End If
        
    If SingComBool = True Then
        ReDim Cmt2exArr(0 To 1) As String
            Cmt2exArr(0) = ""
            Cmt2exArr(1) = "ZilchCom"
        If lngComments = 1 Then
            cmSummary = "COMMENTS:" & vbNewLine & "The comment from " & """" & CmtCol(1) & """" & _
                        " has been extracted." & vbNewLine & vbNewLine & vbNewLine
        ElseIf lngComments >= 2 Then
            cmSummary = "COMMENTS:" & vbNewLine & "All " & lngComments & " comments from " & """" & CmtCol(1) & """" & _
                        " have been extracted." & vbNewLine & vbNewLine & vbNewLine
        End If
        GoTo EndComCount
    ElseIf SingComBool = False Then
n2ex:
        'Choose number of commenters to exclude
        nc2 = InputBox(sCmAuTxt1 & strComExList & vbNewLine & "How many people do you want to exclude?" & vbNewLine & vbNewLine & _
        "Maximum of " & lFAn & ".", "Number to exclude")
        
        'Number validity testing
        If (IsNumeric(nc2) = False) Or (nc2 > (CmtCol.Count - 1)) Then
            rtrn2ex = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract comments" _
            & vbNewLine & vbNewLine & "RETRY to enter valid value" _
            & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
            If rtrn2ex = vbRetry Then
                GoTo n2ex
            
            ElseIf rtrn2ex = vbAbort Then
                cmInc = False: cmEx = False
                ReDim Cmt2exArr(0 To 1) As String
                    Cmt2exArr(0) = ""
                    Cmt2exArr(1) = "ZilchCom"
                GoTo EndComCount
            
            ElseIf rtrn2ex = vbIgnore Then
                cmInc = True: cmEx = False
                ReDim Cmt2exArr(0 To 1) As String
                    Cmt2exArr(0) = ""
                    Cmt2exArr(1) = "ZilchCom"
                cmSummary = "COMMENTS:" & vbNewLine & "All " & lngComments & " comments extracted." & vbNewLine & vbNewLine & vbNewLine
                GoTo EndComCount
            End If
        ElseIf nc2 = 0 Then
            cmInc = True: cmEx = False: comSkip = False
            ReDim Cmt2exArr(0 To 1) As String
                Cmt2exArr(0) = ""
                Cmt2exArr(1) = "ZilchCom"
            cmSummary = "COMMENTS:" & vbNewLine & "All " & lngComments & " comments from " & CmtCol(1) & " extracted." & vbNewLine & vbNewLine & vbNewLine
            GoTo EndComCount
        ElseIf (nc2 >= 1) And (nc2 <= (CmtCol.Count - 1)) Then
            cmInc = True: cmEx = True: comSkip = False
            'Build user-defined list of commenters to exclude
            blDimensioned = False
            For lngIndex = 1 To nc2
            
            'This section builds and populates an array of commenters to exclude
Exn:
                lngAuthExNum = InputBox(sCmAuTxt1 & sTCmAs & vbNewLine & "Enter the number of the person to exclude, from the list above.")
                    If (lngAuthExNum > CmtCol.Count) Or (lngAuthExNum = 0) Or (IsNumeric(lngAuthExNum) = False) Then
                        rtrn2exsel = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract comments" _
                                    & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                                    & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                                    
                        If rtrn2exsel = vbRetry Then
                        GoTo Exn
                        
                        ElseIf rtrn2exsel = vbAbort Then
                            cmInc = False: cmEx = False
                            ReDim Cmt2exArr(0 To 1) As String
                                Cmt2exArr(0) = ""
                                Cmt2exArr(1) = "ZilchCom"
                            GoTo EndComCount
                        
                        ElseIf rtrn2exsel = vbIgnore Then
                            cmInc = True: cmEx = False
                            ReDim Cmt2exArr(0 To 1) As String
                                Cmt2exArr(0) = ""
                                Cmt2exArr(1) = "ZilchCom"
                            cmSummary = "COMMENTS:" & vbNewLine & "All " & lngComments & " comments extracted." & vbNewLine & vbNewLine & vbNewLine
                            GoTo EndComCount
                        End If
                    Else
                        C2X = CmtCol(lngAuthExNum)
                        If blDimensioned = True Then
                            ReDim Preserve Cmt2exArr(0 To UBound(Cmt2exArr) + 1) As String
                        Else
                            ReDim Cmt2exArr(0 To 0) As String
                            Cmt2exArr(0) = ""
                            blDimensioned = True
                        End If
                        Cmt2exArr(UBound(Cmt2exArr)) = C2X
                    End If
            Next
            
            On Error Resume Next
            For Each cd In Cmt2exArr
                Cmt2ex.Add cd, cd
            Next
            
            'Counts number of comments made by authors to exclude
            cmTally = 0
            For lngIndexA = 1 To lngComments
                With oDoc.Comments(lngIndexA)
                    For lngIndex = LBound(Cmt2exArr) To UBound(Cmt2exArr)
                        If .Author = Cmt2exArr(lngIndex) Then cmTally = cmTally + 1
                    Next
                End With
            Next
            
            'Counts number of comments that are included in the tracker
            cmTally = lngComments - cmTally
            
            lngComAusExt = (CmtCol.Count - Cmt2ex.Count)
            
            If lngComAusExt = 1 Then
                strPerPeop = "1 person."
            ElseIf lngComAusExt >= 2 Then
                strPerPeop = lngComAusExt & " people."
            End If
            
            'Text to be displayed at the end
            cmSummary = "COMMENTS:" & vbNewLine & "Extracted:" & vbTab & vbTab & vbTab & cmTally & " comments from " & strPerPeop _
                        & vbNewLine & vbNewLine & "Total in document:" & vbTab & vbTab & lngComments & " comments from" & vbNewLine _
                        & vbTab & vbTab & vbTab & lAn & " people." & vbNewLine & vbNewLine & vbNewLine
        End If
    End If
EndComCount:
End Sub
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Gathers information on the tracked revisions
Public Sub iii_Rev_Analyse()
    Dim lngIndex As Long, lngIndexA As Long, lngRevExNum As Long, lngSingRev As Long, lngRevAusExt As Long
    Dim stReviewer As String, sTReviewrs As String, strRevPerPeop As String, _
        rtrn2Revex As String, revMax As String, selRevs As String, rtrnrvlist As String, R2X As String, RevNum As String, strRevExList As String
    Dim ReviewerArr() As String
    Dim SingRevBool As Boolean
    Dim RevCol As New Collection, ra
    If revSkip = True Then GoTo EndRevCount
    If indelCount = 0 Then
        MsgBox "There are no tracked insertions/deletions in this document.", vbOKOnly + vbCritical
        revInc = False: revEx = False
        ReDim Rev2exArr(0 To 1) As String
            Rev2exArr(0) = ""
            Rev2exArr(1) = "ZilchRev"
        GoTo EndRevCount
    End If
    revInc = False
    SingRevBool = False
    
    'Action if there's only one revision
    If lngRevisions = 1 Then
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        Selection.NextRevision.Range.Select
        With Selection.Range.Revisions(1)
            If .Type = wdRevisionDelete Or wdRevisionInsert Then
                lRn = 1
                revEx = False
                stReviewer = .Author
                ReDim ReviewerArr(0 To 1) As String
                    ReviewerArr(0) = ""
                    ReviewerArr(1) = stReviewer
                
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
            Else
                crsRng.Select
                ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
                Application.ScreenUpdating = True
                MsgBox "There are no tracked insertions/deletions in this document.", vbOKOnly + vbCritical
                revInc = False: revEx = False
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
                GoTo EndRevCount
            End If
        End With
    
    'Options if there are multiple revisions
    ElseIf lngRevisions > 1 Then
        
        MsgBox "Note: Word may appear to freeze at various points. Please be patient." & vbNewLine & vbNewLine & _
                "The more tracked changes there are, the longer the freezes will be.", vbOKOnly + vbInformation, "Word is now processing tracked changes"
        
        Application.Screenrefresh
        Application.ScreenUpdating = False
        Selection.HomeKey Unit:=wdStory
        
        'Builds list of reviewers
        blDimensioned = False
        For lngIndex = 1 To lngRevisions
            Selection.NextRevision
            With Selection.Range.Revisions(1)
                If ((.Type = wdRevisionDelete) Or (.Type = wdRevisionInsert)) _
                And (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") Then
                    stReviewer = .Author
                    If stReviewer <> "" Then
                        If blDimensioned = True Then
                            ReDim Preserve ReviewerArr(0 To UBound(ReviewerArr) + 1) As String
                        Else
                            ReDim ReviewerArr(0 To 0) As String
                            ReviewerArr(0) = ""
                            blDimensioned = True
                        End If
                        ReviewerArr(UBound(ReviewerArr)) = stReviewer
                    End If
                End If
            End With
        Next
    End If
        
    'Collects and counts reviewers
    On Error Resume Next
    For Each ra In ReviewerArr
        RevCol.Add ra, ra
    Next
    
    lRn = RevCol.Count
    
    crsRng.Select
    ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
    Application.ScreenUpdating = True
    
    'Limits options if there is only 1 reviewer
    If RevCol.Count = 1 Then
        If indelCount = 1 Then
            RevNum = "There is only one tracked insertion/deletion from: " & RevCol(1) & _
                        "." & vbNewLine & vbNewLine & "Do you want to extract their tracked change?"
        ElseIf indelCount > 1 Then
            RevNum = "There are " & indelCount & " tracked insertions/deletions from: " & RevCol(1) & _
                        "." & vbNewLine & vbNewLine & "Do you want to extract their tracked changes?"
        End If
        If MsgBox(RevNum, vbYesNo + vbQuestion) = vbYes Then
            revInc = True: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            If indelCount = 1 Then
                revSummary = "REVISIONS:" & vbNewLine & "The tracked insertions/deletion from " & """" & RevCol(1) & """" & " has been extracted." & vbNewLine & vbNewLine & vbNewLine
            ElseIf indelCount >= 2 Then
                revSummary = "REVISIONS:" & vbNewLine & "All " & indelCount & " tracked insertions/deletions from " & """" & RevCol(1) & """" & " have been extracted." & vbNewLine & vbNewLine & vbNewLine
            End If
            GoTo EndRevCount
        Else
            revInc = False: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            revSummary = ""
            GoTo EndRevCount
        End If
            
    'Options if there are multiple reviewers
    ElseIf RevCol.Count > 1 Then
        strRevExList = ""
        sTReviewrs = "To exclude nobody, type 0" & vbNewLine & _
                    "To cancel extracting revisions, type " & (lRn + 1) & vbNewLine & _
                    "To cancel and exit, type " & (lRn + 2) & vbNewLine & vbNewLine & _
                    "The following people have made comments:" & vbNewLine & vbNewLine
        For lngIndex = 1 To lRn
            sTReviewrs = sTReviewrs & lngIndex & ". " & RevCol(lngIndex) & vbNewLine
            strRevExList = strRevExList & lngIndex & ". To exclude: " & RevCol(lngIndex) & vbNewLine
        Next
        
        sTReviewrs = sTReviewrs & vbNewLine
        
        If RevCol.Count > 2 Then
            lFRevn = RevCol.Count - 1
            revMax = "You can exclude tracked insertions/deletions from a maximum of " & lFRevn & " people." _
                & vbNewLine & vbNewLine & "How many people do you want to exclude?"
        ElseIf RevCol.Count = 2 Then
            SingRevBool = True
            lFRevn = 1
            revMax = "You can exclude tracked insertions/deletions from a maximum of one person."
        End If
    End If
    
    'Decide whether to include tracked changes in the tracker
    'Actions to take if a maximum of 1 person can be excluded
SingleReview:
    If SingRevBool = True Then
        lngSingRev = InputBox(revMax & vbNewLine & vbNewLine & strRevExList)
        If (IsNumeric(lngSingRev) = False) Or (lngSingRev > (lRn + 2)) Then
           MsgBox "Invalid option selected. Please try again.", vbOKOnly + vbCritical
           GoTo SingleReview
        ElseIf lngSingRev = 0 Then
            revInc = True: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            revSummary = "REVISIONS:" & vbNewLine & "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted." & vbNewLine & vbNewLine & vbNewLine
            GoTo EndRevCount
        ElseIf (lngSingRev = 1) Or (lngSingRev = 2) Then
            R2X = RevCol(lngSingRev)
            revInc = True: revEx = True
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = R2X
        ElseIf lngSingRev = 3 Then
            revInc = False: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            revSummary = ""
            GoTo EndRevCount
        ElseIf lngSingRev = 4 Then
            MsgBox "Process terminated.", vbOKOnly + vbCritical
            Set oDoc = Nothing
            End
        End If
    End If
            
    'This section gives options for the number of people to exclude (if any)
    If SingRevBool = False Then
nrv2ex:
        'Choose number of reviewers to exclude
        rev2exN = InputBox(sTReviewrs & vbNewLine & vbNewLine & _
                revMax, "Number to exclude")
        
        'Number validity testing
        If (IsNumeric(rev2exN) = False) Or (rev2exN = lRn) Or (rev2exN > (lRn + 2)) Then
            rtrn2Revex = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract revisions" _
            & vbNewLine & vbNewLine & "RETRY to enter valid value" _
            & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
            If rtrn2Revex = vbRetry Then
                GoTo nrv2ex
            ElseIf rtrn2Revex = vbAbort Then
                revInc = False: revEx = False
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
                GoTo EndRevCount
            ElseIf rtrn2Revex = vbIgnore Then
                revInc = True: revEx = False
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
                revSummary = "REVISIONS:" & vbNewLine & "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted." & vbNewLine & vbNewLine & vbNewLine
                GoTo EndRevCount
            End If
        ElseIf rev2exN = (lRn + 1) Then
            revInc = False: revEx = False
            ReDim Rev2exArr(0 To 1) As String
                Rev2exArr(0) = ""
                Rev2exArr(1) = "ZilchRev"
            revSummary = ""
            GoTo EndRevCount
        ElseIf rev2exN = (lRn + 2) Then
            MsgBox "Process terminated.", vbOKOnly + vbCritical
            Set oDoc = Nothing
            End
        ElseIf rev2exN = 0 Then
            revInc = True: revEx = False
                ReDim Rev2exArr(0 To 1) As String
                    Rev2exArr(0) = ""
                    Rev2exArr(1) = "ZilchRev"
                revSummary = "REVISIONS:" & vbNewLine & "All " & indelCount & " insertions/deletions from all " & lRn & " people extracted." & vbNewLine & vbNewLine & vbNewLine
                GoTo EndRevCount
        ElseIf (rev2exN >= 1) And (rev2exN <= lFRevn) Then
            
            'Build user-defined list of reviewers to exclude
            revInc = True: revEx = True
            blDimensioned = False
            For lngIndex = 1 To rev2exN
Revexlist:
                lngRevExNum = InputBox("Enter the list number of the person to exclude:" & _
                            vbNewLine & vbNewLine & strRevExList)
                    If (lngRevExNum > RevCol.Count) Or (lngRevExNum = 0) Or (IsNumeric(lngRevExNum) = False) Then
                        rtrnrvlist = MsgBox("Invalid value." & vbNewLine & vbNewLine & "ABORT to not extract revisions" _
                                    & vbNewLine & vbNewLine & "RETRY to enter valid value" _
                                    & vbNewLine & vbNewLine & "IGNORE to proceed without excluding anyone.", vbAbortRetryIgnore + vbCritical)
                                    
                                    If rtrn2Revex = vbRetry Then
                                        GoTo Revexlist
                                    ElseIf rtrn2Revex = vbAbort Then
                                        revInc = False: revEx = False
                                        ReDim Rev2exArr(0 To 1) As String
                                            Rev2exArr(0) = ""
                                            Rev2exArr(1) = "ZilchRev"
                                        GoTo EndRevCount
                                    ElseIf rtrn2Revex = vbIgnore Then
                                        revInc = True: revEx = False
                                        ReDim Rev2exArr(0 To 1) As String
                                            Rev2exArr(0) = ""
                                            Rev2exArr(1) = "ZilchRev"
                                        revSummary = "REVISIONS:" & vbNewLine & "All " & indelCount & " insertions/deletions from all " & lRn & _
                                                    " people extracted." & vbNewLine & vbNewLine & vbNewLine
                                        GoTo EndRevCount
                                    End If
                    Else
                        R2X = RevCol(lngRevExNum)
                        
                        If blDimensioned = True Then
                            ReDim Preserve Rev2exArr(0 To UBound(Rev2exArr) + 1) As String
                        Else
                            ReDim Rev2exArr(0 To 0) As String
                            Rev2exArr(0) = ""
                            blDimensioned = True
                        End If
                        Rev2exArr(UBound(Rev2exArr)) = R2X
                    End If
            Next
        End If
    End If
            
    On Error Resume Next
    For Each rd In Rev2exArr
        Review2ex.Add rd, rd
    Next
        
            
            
    Application.ScreenUpdating = False
    Selection.HomeKey Unit:=wdStory
    
    'Counts number of changes made by reviewers to exclude
    revTally = 0
    For lngIndex = 1 To lngRevisions
        With Selection.NextRevision
            If (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") And ((.Type = wdRevisionDelete) Or (.Type = wdRevisionInsert)) Then
                For lngIndexA = LBound(Rev2exArr) To UBound(Rev2exArr)
                    If .Author = Rev2exArr(lngIndexA) Then revTally = revTally + 1
                Next
            End If
        End With
    Next
    
    'Counts number of changes that are included in the tracker
    revTally = indelCount - revTally
            
    lngRevAusExt = (RevCol.Count - Review2ex.Count)
    
    If lngRevAusExt = 1 Then
        strRevPerPeop = "1 person."
    ElseIf lngRevAusExt >= 2 Then
        strRevPerPeop = lngRevAusExt & " people."
    End If
    
    'Text to display at the end
    revSummary = "REVISIONS:" & vbNewLine & "Extracted:" & vbTab & vbTab & vbTab & revTally & " tracked insertions/deletions" & vbNewLine _
                & vbTab & vbTab & vbTab & "from " & strRevPerPeop & vbNewLine & vbNewLine & "Total in document:" _
                & vbTab & vbTab & indelCount & " tracked insertions/deletions" & vbNewLine _
                & vbTab & vbTab & vbTab & "from " & lRn & " people." & vbNewLine & vbNewLine & vbNewLine
    
    crsRng.Select
    ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
    Application.ScreenUpdating = True
    Application.Screenrefresh
            
EndRevCount:
End Sub
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Makes the grid
Public Sub iv_Grid_maker()
Dim oNewDoc As Document
Dim oTbl As Table
Dim NXTA As Boolean, NXTR As Boolean
Dim lngIndex As Long, lngComments As Long, lngRow As Long, lngIndexA As Long, lngIndexB As Long
Dim oRevRange As Range
Dim Rvtype As String, Rvpage As String, Rvsort As String, Rvauth As String, Rvtext As String
    
  Set oDoc = ActiveDocument
  lngRevisions = oDoc.Revisions.Count
  lngComments = oDoc.Comments.Count
  If cmInc = False And revInc = False Then
    MsgBox "No comments or revisions selected.", vbOKOnly + vbInformation
    GoTo lbl_Exit
  End If
  Application.ScreenUpdating = False
  
  'This section builds the initial grid
  Set oNewDoc = Documents.Add
  With oNewDoc
    .PageSetup.Orientation = wdOrientLandscape
    Select Case True
      Case cmInc And revInc
       .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = "Comments and revisions extracted from: " & oDoc.Name
      Case cmInc And Not revInc
        .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = "Comments extracted from: " & oDoc.Name
      Case revInc And Not cmInc
        .Sections(1).Headers(wdHeaderFooterPrimary).Range.Text = "Revisions extracted from: " & oDoc.Name
    End Select
    With .Styles(wdStyleNormal)
      .Font.Name = "Calibri"
      .Font.Size = 9
      .ParagraphFormat.LeftIndent = 0
      .ParagraphFormat.SpaceAfter = 6
    End With
    With .Styles(wdStyleHeader)
      .Font.Size = 8
      .ParagraphFormat.SpaceAfter = 0
    End With
    Set oTbl = .Tables.Add(Selection.Range, lngComments + lngRevisions + 1, 7)
    With oTbl
      .Range.Style = wdStyleNormal
      .AllowAutoFit = False
      .PreferredWidthType = wdPreferredWidthPercent
      .PreferredWidth = 100
      .Columns.PreferredWidthType = wdPreferredWidthPercent
      .Columns(1).PreferredWidth = 5
      .Columns(2).PreferredWidth = 10
      .Columns(3).PreferredWidth = 25
      .Columns(4).PreferredWidth = 25
      .Columns(5).PreferredWidth = 15
      .Columns(6).PreferredWidth = 30
      .Columns(7).PreferredWidth = 2
      With .Rows(1)
        .HeadingFormat = True
        .Range.Font.Bold = True
        .Cells(1).Range.Text = "Page"
        .Cells(2).Range.Text = "Type"
        .Cells(3).Range.Text = "Comment"
        .Cells(4).Range.Text = "Relevant text"
        .Cells(5).Range.Text = "Commenter"
        .Cells(6).Range.Text = "Action/response"
        'The sort column is just for sorting revisions and comments by line number. It is deleted during finalisation
        .Cells(7).Range.Text = "Sort"
      End With
    End With
End With
    
    'Collects comments for the grid
    If cmInc = True Then
      lngRow = 1
      For lngIndex = 1 To lngComments
        With oDoc
        NXTA = False
        If cmEx = True Then
          For lngIndexA = LBound(Cmt2exArr) To UBound(Cmt2exArr)
            If .Comments(lngIndex).Author = Cmt2exArr(lngIndexA) Then NXTA = True
          Next
        End If
        If NXTA = False Then
          lngRow = lngRow + 1
          oTbl.Rows.Add
          With oTbl.Rows(lngRow)
            .Cells(1).Range.Text = oDoc.Comments(lngIndex).Scope.Information(wdActiveEndPageNumber)
            .Cells(2).Range.Text = "Comment"
            .Cells(3).Range.Text = oDoc.Comments(lngIndex).Range.Text
            .Cells(4).Range.Text = oDoc.Comments(lngIndex).Scope
            .Cells(5).Range.Text = oDoc.Comments(lngIndex).Author
            .Cells(7).Range.Text = oDoc.Comments(lngIndex).Scope.Information(wdFirstCharacterLineNumber) 'For sorting
           End With
        End If
        End With
      Next
    End If
    
    'Collects tracked insertions and deletions for the grid
    If revInc Then
        Application.ScreenUpdating = False
        With oDoc
        Selection.HomeKey Unit:=wdStory
        
        If (cmInc = False) Or (comSkip = True) Then lngRow = 1
        On Error GoTo NextRevb
        For lngIndex = 0 To lngRevisions
        
            With oDoc
                With Selection.NextRevision
                    NXTR = False
                    If revEx = True Then
                        For lngIndexB = LBound(Rev2exArr) To UBound(Rev2exArr)
                            If .Author = Rev2exArr(lngIndexB) Then NXTR = True
                        Next
                    End If
                    If NXTR = False Then
                        lngRow = lngRow + 1
                        If (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") And (.Type = wdRevisionDelete) Then
                          Rvtype = "Delete"
                          Rvpage = .Range.Information(wdActiveEndPageNumber)
                          Rvauth = .Author
                          Rvsort = .Range.Information(wdFirstCharacterLineNumber)
                          Rvtext = """" & .Range.Text & """"
                        ElseIf (.Range.Text Like "*[ A-z0-9\,\.\?\(\)\;]*") And (.Type = wdRevisionInsert) Then
                          Rvtype = "Insert"
                          Rvpage = .Range.Information(wdActiveEndPageNumber)
                          Rvauth = .Author
                          Rvsort = .Range.Information(wdFirstCharacterLineNumber)
                          Rvtext = """" & .Range.Text & """"
                        Else
                          Rvtype = ""
                          Rvpage = ""
                          Rvauth = ""
                          Rvsort = ""
                          Rvtext = ""
                        End If
                    End If
                End With
            End With
            If NXTR = False Then
                With oNewDoc
                    oTbl.Rows.Add
                    With oTbl.Rows(lngRow)
                        .Cells(1).Range.Text = Rvpage
                        .Cells(2).Range.Text = Rvtype
                        .Cells(4).Range.Text = Rvtext
                        .Cells(5).Range.Text = Rvauth
                        .Cells(7).Range.Text = Rvsort
                        
                        If Rvtype = "Delete" Then
                          .Cells(2).Range.Font.Color = wdColorRed
                          .Cells(4).Range.Font.Color = wdColorRed
                        ElseIf Rvtype = "Insert" = True Then
                          .Cells(2).Range.Font.Color = wdColorBlue
                          .Cells(4).Range.Font.Color = wdColorBlue
                        End If
                    End With
                End With
            End If
NextRevb:
        oDoc.Activate
        Next
        End With
    End If
  oDoc.Activate
  crsRng.Select
  ActiveWindow.ActivePane.VerticalPercentScrolled = scrllPs
Finalise:
  oNewDoc.Activate
  With oTbl.Borders 'Applies line style to the grid
    .InsideLineStyle = wdLineStyleSingle
    .OutsideLineStyle = wdLineStyleSingle
  End With
  oTbl.Select
  
  'This sorts the table entries by page number and location in page
  With Selection
    .Sort ExcludeHeader:=True, FieldNumber:="Column 1", SortFieldType _
    :=wdSortFieldNumeric, SortOrder:=wdSortOrderAscending, FieldNumber2:= _
    "Column 7", SortFieldType2:=wdSortFieldNumeric, SortOrder2:= _
    wdSortOrderAscending, FieldNumber3:="", SortFieldType3:= _
    wdSortFieldAlphanumeric, SortOrder3:=wdSortOrderAscending, Separator:= _
    wdSortSeparateByCommas, SortColumn:=False, CaseSensitive:=False, _
    LanguageID:=wdEnglishUK, SubFieldNumber:="Paragraphs", SubFieldNumber2:= _
    "Paragraphs", SubFieldNumber3:="Paragraphs"
    .Columns(7).Delete
  End With
  
  'Deletes any blank rows that have crept in
  With oTbl
    For lngIndex = .Rows.Count To 1 Step -1
      If Len(.Rows(lngIndex).Range.Text) = 14 Then .Rows(lngIndex).Delete
    Next lngIndex
  End With
  Application.ScreenUpdating = True
  Application.Screenrefresh
  oNewDoc.Activate
  MsgBox cmSummary & revSummary & "Finished creating tracker.", vbOKOnly + vbInformation, "Job summary"
lbl_Exit:
  Set oNewDoc = Nothing: Set oTbl = Nothing
End Sub
gmaxey
07-13-2018, 08:47 AM
You are probably about ready to take this to the next level.  Your message box Choose 1, 2, 3 or 4 should consider clicking the "X" or the "Cancel" button the same as entering 4.
Better yet, why not have a userform with checkbox for the user to decide how to proceed and a couple of multiselect listbox to choose which commenters, editors to include/exclude.
vbCritcal is usually associated with something critical.  Consider vbInfomation.
h2whoa
07-13-2018, 09:06 AM
You are probably about ready to take this to the next level.  Your message box Choose 1, 2, 3 or 4 should consider clicking the "X" or the "Cancel" button the same as entering 4.
Better yet, why not have a userform with checkbox for the user to decide how to proceed and a couple of multiselect listbox to choose which commenters, editors to include/exclude.
vbCritcal is usually associated with something critical.  Consider vbInfomation.
Yes, that would be perfect! I actually tried to do that, but wasn't sure how to not have it treat Cancel the same as "" + OK. I wanted to try and make sure that if a user accidentally pressed OK without inputting a value they would get the opportunity to retry, and I was beating my head against the wall for a bit before I decided to move on.
Take your point about vbCritical as well. It's a good suggestion, and I'll update that in the code.
Powered by vBulletin® Version 4.2.5 Copyright © 2025 vBulletin Solutions Inc. All rights reserved.