Spire.PDF is a professional PDF library applied to creating, writing, editing, handling and reading PDF files without any external dependencies. Get free and professional technical support for Spire.PDF for .NET, Java, Android, C++, Python.

Wed Jul 13, 2022 1:45 pm

We have some code to redact certain phrases in a Pdf document that is working fine. This is some important code to us, so I'm trying to write some tests around this to make sure that when asked to redact a phrase it does, it's in the right place, colour, opacity, etc. I cannot find how to do this in code.

I know there are issues with relying on this alone for redaction. We are not doing that, this is just one part of a larger process. This question is about unit testing, not our operating procedure.

Here's how we are adding the boxes

Code: Select all
private static void HideText(PdfPageBase page, string text, TextFindParameter searchFindParameter)
{
    var textFindCollection = page.FindText(text, searchFindParameter);
   
    if (textFindCollection is null)
    {
        return;
    }

    foreach (var textFind in textFindCollection.Finds)
    {
        page.Canvas.DrawRectangle(PdfBrushes.Black, textFind.Bounds);
    }
}

My question is: How do I get the shapes in the page, specifically the rectangle just drawn, after this?

The only populated collection in page after this PageLayers, but I've not found anything of use in there. ExtractImages returns nothing, which is not surprising as these are Shapes.

I imagine I need to cast something as something else to be able to get to the Shapes, but I cannot find out what. I found an example that went through Section Tables, but I cannot find a Tables collection anywhere.

redmorris
 
Posts: 4
Joined: Wed Jul 13, 2022 1:37 pm

Thu Jul 14, 2022 7:29 am

Hi,

Thank you for your inquiry.
Kindly note our Spire.PDF does not provide a method to get the rectangle you drew, but you can use the PdfTextMarkupAnnotation object to achieve your requirement. Please refer to the code below. If there is any question, please feel free to write back.
Code: Select all
            PdfDocument doc = new PdfDocument();
            doc.LoadFromFile("test.pdf");
            PdfPageBase page = doc.Pages[0];
            //find keyword
            PdfTextFind[] finds = page.FindText(keyword, Spire.Pdf.General.Find.TextFindParameter.None).Finds;
            //draw PdfTextMarkupAnnotation according to keyword bound
            foreach (PdfTextFind find in finds)
            {
                RectangleF rect = find.TextBounds[0];
                PdfTextMarkupAnnotation annotation1 = new PdfTextMarkupAnnotation("", "", rect);
                annotation1.Border = new PdfAnnotationBorder(0.75f);
                annotation1.TextMarkupColor = Color.Black;
                find.SearchPage.AnnotationsWidget.Add(annotation1);
            }
            //get TextMarkupAnnotation
            for (int i = 0; i < page.AnnotationsWidget.Count; i++)
            {
                if (page.AnnotationsWidget[i] is PdfTextMarkupAnnotation)
                {
                    //.......                     
                }
            }

Sincerely,
Kylie
E-iceblue support team
User avatar

kylie.tian
 
Posts: 412
Joined: Mon Mar 07, 2022 2:30 am

Mon Jul 18, 2022 11:29 am

You code (almost) worked. Thanks

I found that the PdfTextMarkupAnnotation constructor ignores the size attributes of a passed RectangleF, and I had to set it in a subsequent line, e.g.,

Code: Select all
var rect = textFind.TextBounds[0];
var annotation = new PdfTextMarkupAnnotation("", "", rect);
annotation.Size = rect.Size;


Also, is there a way to make the highlight full opacity so that the text beneath is it unreadable? Without this this solution doesn't suit our needs as this is a step in a redaction process

Alternatively, we could use textFind.ApplyRecoverString(text, Color.Black); but is it possible to determine the background colour of another TextFind in the test, or a region of the document from X, Y, Width and Height we can get from the TextFind?

redmorris
 
Posts: 4
Joined: Wed Jul 13, 2022 1:37 pm

Tue Jul 19, 2022 7:17 am

Hi,

Thank you for your reply.
Sorry PdfTextMarkupAnnotation doesn't provide a way to make the highlight full opacity. Yes, you can use the ApplyRecoverString method to cover text with black color. Please refer to the following code to get the X, Y, Width and Height, but sorry the background color of TextFind cannot be determined at present.
Code: Select all
                       
                        find.ApplyRecoverString(text, Color.Black);
                        float x = find.Bounds.X;
                        float y = find.Bounds.Y;
                        float width = find.Bounds.Width;
                        float height = find.Bounds.Height;

Sincerely,
Kylie
E-iceblue support team
User avatar

kylie.tian
 
Posts: 412
Joined: Mon Mar 07, 2022 2:30 am

Tue Jul 19, 2022 8:31 am

Hi Kylie,

I don't think I'm explaining myself well. This is for a Unit Test. So some other code will have already modified the document by drawing, using ApplyRecoverString, etc. In the Unit Test we must be able to find that redaction to ensure it was actually applied. This means we can't use the same find object we used to create the redaction

redmorris
 
Posts: 4
Joined: Wed Jul 13, 2022 1:37 pm

Tue Jul 19, 2022 10:17 am

Hi,

Kindly note that the ApplyRecoverString method just cover original text with color, and the original text still exists. Please refer to the code below to find it again.
Code: Select all
            PdfDocument pdf = new PdfDocument();
            pdf.LoadFromFile("res.pdf");
            PdfTextFind[] finds = null;
            foreach (PdfPageBase page in pdf.Pages)
            {
                finds = page.FindText("T", TextFindParameter.None).Finds;
                foreach (PdfTextFind find in finds)
                {
                    float x = find.Bounds.X;
                    float y = find.Bounds.Y;
                    float width = find.Bounds.Width;
                    float height = find.Bounds.Height;
                }
              }


Sincerely,
Kylie
E-iceblue support team
User avatar

kylie.tian
 
Posts: 412
Joined: Mon Mar 07, 2022 2:30 am

Tue Jul 19, 2022 11:22 am

Thanks Kylie, there are other steps after this one to further protect the document.

How can I extend the code you provided to get the background colour within those bounds, i.e., how can I test if the code that should have applied ApplyRecoverString did indeed run?

redmorris
 
Posts: 4
Joined: Wed Jul 13, 2022 1:37 pm

Wed Jul 20, 2022 10:09 am

Hi,

Please note that the background color cannot be obtained. As I mentioned earlier, the ApplyRecoverString method is used to cover original text, so you can judge by finding the original text. Maybe you can achieve it combine with PdfTextMarkupAnnotation object. You can add the ApplyRecoverString method to to cover the original annotation with a black background, and then you find the black background by looking for the annotation. Please refer to the code below.
Code: Select all
           Please refer to the code below.
           PdfDocument doc = new PdfDocument();
            doc.LoadFromFile("test1.pdf");
            PdfPageBase page = doc.Pages[0];
            //find keyword
             PdfTextFind[] finds = page.FindText("test", Spire.Pdf.General.Find.TextFindParameter.IgnoreCase).Finds;
            //draw PdfTextMarkupAnnotation according to keyword bound
            foreach (PdfTextFind find in finds)
            {
                RectangleF rect = find.TextBounds[0];
                PdfTextMarkupAnnotation annotation1 = new PdfTextMarkupAnnotation("", "", rect);
                annotation1.TextMarkupColor = Color.Black;
                find.SearchPage.AnnotationsWidget.Add(annotation1);
                //cover the original annotation with a black background
                find.ApplyRecoverString(" ", Color.Black);
            }
            //get TextMarkupAnnotation
            for (int i = 0; i < page.AnnotationsWidget.Count; i++)
            {
                if (page.AnnotationsWidget[i] is PdfTextMarkupAnnotation)
                {
                    //.......                     
                }
            }

Sincerely,
Kylie
E-iceblue support team
User avatar

kylie.tian
 
Posts: 412
Joined: Mon Mar 07, 2022 2:30 am

Wed Oct 19, 2022 3:43 am

Hi,

Greetings from E-iceblue!
Did my code fix your issue? I would appreciate it much if you can give me some feedback at your convenience.

Sincerely,
Kylie
E-iceblue support team
User avatar

kylie.tian
 
Posts: 412
Joined: Mon Mar 07, 2022 2:30 am

Return to Spire.PDF

cron