FindAndRedact.vb
''
'' This code is part of GrapeCity Documents for PDF samples.
'' Copyright (c) GrapeCity, Inc. All rights reserved.
''
Imports System.IO
Imports System.Drawing
Imports System.Text.RegularExpressions
Imports GrapeCity.Documents.Pdf
Imports GrapeCity.Documents.Pdf.Annotations
Imports GrapeCity.Documents.Pdf.AcroForms

'' This sample shows how to use the text map to find specific content 
'' in a PDF And mark it for redaction.
'' Note that currently GcPdf does Not yet allow to actually apply
'' the redactions (i.e. remove the content) - but it does allow
'' to enumerate, add Or edit redact annotations.
'' The resulting PDF can be then loaded into Acrobat to review
'' And apply redactions interactively.
'' The PDF used in this sample was created by TimeSheet.
Public Class FindAndRedact
    Public Function CreatePDF(ByVal stream As Stream) As Integer
        Dim doc = New GcPdfDocument()
        Using fs As New FileStream(Path.Combine("Resources", "PDFs", "TimeSheet.pdf"), FileMode.Open, FileAccess.Read)
            doc.Load(fs)

            '' Note: Acrobat does Not allow To apply redactions In a digitally signed
            '' document, so first we find And remove any existing signatures:
            RemoveSignatureFields(doc.AcroForm.Fields)

            '' Loop through pages, removing anything that looks Like a short date
            For Each page In doc.Pages
                Dim tmap = page.GetTextMap()
                For Each tline In tmap
                    If (Regex.Match(tline.Text.Trim(), "\d+[/-]\w+[/-]\d").Success) Then
                        Dim redact = New RedactAnnotation() With
                            {
                                .Rect = tline.GetCoords().ToRect(),
                                .Color = Color.Red,
                                .Page = page,
                                .MarkBorderColor = Color.Red,
                                .MarkFillColor = Color.Yellow
                            }
                        '' If we hadn't already set redact.Page = page, we could do this:
                        '' page.Annotations.Add(redact)
                    End If
                Next
            Next
            '' Done
            doc.Save(stream)
            Return doc.Pages.Count
        End Using
    End Function

    '' This code Is from the RemoveSignatureFields sample:
    Sub RemoveSignatureFields(ByVal fields As FieldCollection)
        For i = fields.Count - 1 To 0 Step -1
            RemoveSignatureFields(fields(i).Children)
            If TypeOf fields(i) Is SignatureField Then
                fields.RemoveAt(i)
            End If
        Next
    End Sub
End Class