« MBS FileMaker Plugin,… | Home | DynaPDF Manual online… »

Embedded links with MBS and DynaPDF in Xojo

Perhaps you have a PDF document and want to add some links to the PDF. You want to add some page links to navigate inside the PDF Document and jump to the right pages or websites. Maybe you want to change the target of a linked url in the document. With the MBS Xojo DynaPDF Plugin for Xojo you can do it in an easy way. Now I want to show you how to do it.

Initialize and load PDF
At first we need to initialized DynaPDF and put, if you have one, the license key in the document:

Dim pdf As New MyDynapdfMBS

Then we call the open dialog for choosing the PDF for import. Next we ask the user where to store the final PDF file. If the saving dialog is canceled (outFile=Nil) the script return.

Dim f As FolderItem = GetOpenFolderItem(MyFileTypes.Pdf)
Dim outFile As folderitem = GetSaveFolderItem(MyFileTypes.Pdf, "PDF with links.pdf")
If outFile = Nil Then Return

Now we create a new and empty PDF at the given file. Pass nil instead to create an in-memory PDF:

Call pdf.CreateNewPDF(outFile)

We subsequently set flags for the import. We want pages (not templates) and get all parts of the pages. By asking to use visible coordinates, our coordinates are relative to pages crop box (if existent) and honors the orientation of the page.

dim flags as integer = Bitwise.BitOr(pdf.kifImportAsPage, pdf.kifImportAll)
Call pdf.SetImportFlags(flags)
Call pdf.SetUseVisibleCoords(True)

kifImportAsPage constant set the import options for import the page as pages and not as a template. With the setting kifImportAll all elements of the source PDF are imported. For example you can only import the bookmarks or all elements except the annotations.

After that we open our import file and import it page wise to our pdf:

Call pdf.openimportFile(f, pdf.kptopen, "")
Call pdf.ImportPDFFile(pdf.GetPageCount + 1, 1.0, 1.0)
call pdf.CloseImportFile

pdf.GetPageCount+1 define the destination page number. We use this to be able to call import in a loop and import new pages after existing ones.

Changing target URL
At first we want to detect an existing link and change the target link.

We finde the annotation ID by the current url of the link. The annotation ID is an integer value which identifies the link, usually it is the index within the list of annotations. The ID is unique in the document. Every existing and added link has an unique ID.

Dim annot As Integer = pdf.FindLinkAnnot(ā€˛https://www.monkeybreadsoftware.com")

We need the annotation ID to change the target url. With pdf.ChangeLinkAnnot we change the URL of the annotation. The new target weblink is passed as parameter.

Call pdf.ChangeLinkAnnot annot, "https://monkeybreadsoftware.net/class-continuitycamerambs.shtml"

Page links
Now we want to add a page link on the first page. In the example our first page is a directory, which includes the headings of the sections. We want to position the first link over the first entry of the directory.
We add the page link to the first side with:

annotID = pdf.PageLink(57.0, 651, 105.015, 15, 2)

With the first four parameter we define the position and size of the link box. The link box is a translucent rectangle which overlay an area. If we click to this area we activates the link and jump to the target page. Because of this we positioning the rectangle over the directory entry. The first two parameters define the coordinates of the left-down edge of the rectangle. The third and forth parameter are height and width of the rectangle. The fifth parameter of the function specifies the page, at that we want to go. With a click on the link rectangle we jump to the Top of the indicated page.

If we want to jump directly to a caption, how is maybe in the middle of the page, we need the pdf.PageLinkEx function. In addition to the coordinates of the link rectangle we can specified the position we want to jump too.

annotID = pdf.PageLinkEx(57, 617, 152.490, 15, pdf.kdtXY_Zoom, 2, 57, 617, 1, 1)

The first four parameters determine the link rectangle again. The fifth parameter defines the destination type of the link. That means we can define what happens with the additional parameters. You can jump and provide X/Y and zoom factor (kdtXY_Zoom), provide no parameters for e.g. kdtFit to just fit to the page or e.g. kdtFit_Rect with 4 parameters for the rectangles. See dynapdf_help.pdf, the DynaPDF manual for details on the options (around page 541) or the online version.

Web Link
Now we want to add an embedded web link to our PDF document. In order to do this, we write a text in the pdf and overlay a weblink with the text.

We write the text with the following code lines in Xojo:

Call pdf.SetFont "Arial", pdf.kfsUnderlined, 12, True, pdf.kcpUnicode
Call pdf.SetFillColorSpace(pdf.kcsDeviceRGB)
Call pdf.SetFillColor(pdf.RGB(0, 0, 0))
Call pdf.WriteText 57, 60, "weblink to MBS"

With setFont we set the font, the font style, font size, wether the font is embedded or not and the page code. Our text should be in font Arial, underlined and in font size 12. For code page we always use cpUnicode nowadays unless you have a specific compatibility need to very old PDF viewers not supporting Unicode.
SetFillColor changes the colors of added elements. In this case, our text. We use the RGB function and for that, make sure with SetFillColorSpace earlier to use RGB color space.
WriteText set the position of the text and draws the text itself. In our example we write: weblink to MBS. Then we can overlay the weblink with:

annot = pdf.WebLink(57, 60, 100, 7, "https://www.monkeybreadsoftware.net/topic-dynapdf.shtml")

The first forth parameter defines the link rectangle again. The last parameter is a string with the target url. You can use GetTextWidth to measure width of a text.

I hope that this functions are useful for you. You may need to purchase a MBS Xojo DynaPDF Plugin license in Lite or higher level.

If you have questions, please do not hesitate to contact me.
By Stefanie Juchmes
19 07 19 - 10:11