Search code examples
c#pdfoverwriteitext7bookmarks

How to overwrite an existing bookmark tree in a PDF using iText7


I'm developping an utility that take tab incremented text file as an input to create a bookmark tree (aka outlines) in an existing PDF file, using iText7.

Obvisously this is not the real code, but this is basically how I build the tree:

PdfReader reader = new PdfReader(srcFilePath);
PdfWriter writer = new PdfWriter(targetFilePath);
PdfDocument pdfDoc = new PdfDocument(reader, writer);

PdfOutline rootOutline = pdfDoc.GetOutlines(false);
PdfOutline mainTitleOutline;

(mainTitleOutline = rootOutline.AddOutline("Title 1")).AddDestination(PdfExplicitDestination.CreateFit(pdfDoc.GetPage(1)));
mainTitleOutline.AddOutline("Sub title 1.1").AddDestination(PdfExplicitDestination.CreateFit(pdfDoc.GetPage(2)));
mainTitleOutline.AddOutline("Sub title 1.2").AddDestination(PdfExplicitDestination.CreateFit(pdfDoc.GetPage(3)));

(mainTitleOutline = rootOutline.AddOutline("Title 2")).AddDestination(PdfExplicitDestination.CreateFit(pdfDoc.GetPage(4)));
mainTitleOutline.AddOutline("Sub title 2.1").AddDestination(PdfExplicitDestination.CreateFit(pdfDoc.GetPage(5)));
mainTitleOutline.AddOutline("Sub title 2.2").AddDestination(PdfExplicitDestination.CreateFit(pdfDoc.GetPage(6)));

pdfDoc.Close();

This works pretty well when the PDF doesn't already have any bookmark, but when there are (pdfDoc.GetOutlines(false).GetAllChildren().Count > 0), I'd like to delete the whole tree before hand (hence overwrite them), because if I don't, I end up ADDING the new outlines to the old ones.

Is there a way to do it?


Solution

  • This piece of convenient API is indeed something that is missing now but you can still do it on a low level with one line of code:

     pdfDocument.GetCatalog().GetPdfObject().Remove(PdfName.Outlines);
    

    Just make sure to remove the outlines before you access them first time, i.e.:

    PdfReader reader = new PdfReader(srcFilePath);
    PdfWriter writer = new PdfWriter(targetFilePath);
    PdfDocument pdfDoc = new PdfDocument(reader, writer);
    
    // Remove outlines before getting PdfOutline object by calling GetOutlines
    pdfDocument.GetCatalog().GetPdfObject().Remove(PdfName.Outlines);
    PdfOutline rootOutline = pdfDoc.GetOutlines(false);