How To Build A Customized PDF That Functions Like A Portfolio
This method is highly customizable, using attachments as the "other" files inside the PDF file.
In my last post I described how to create a PDF portfolio - a collection of files inside one PDF file.
There's another method that uses PDF attachments as “the other files” contained in the PDF file. Like the portfolio, these other files do not have to be PDF files. But unlike the portfolio, these files can easily be opened with the software application that opens those file types by simply double-clicking them in he attachments panel. They can then be modified and saved back into the PDF if necessary.
For example, you can attach an Excel spreadsheet, a Word document, a text file, or many other types of files, and the user can open them, modify them, and save them inside the PDF. When the PDF is saved, so to will be the changes to the file attachments.
Three Ways To Add Attachments
1. The Acrobat User Interface (UI)
Open the attachments panel, click the paperclip icon, and browse for the file.
2. Use a script
In scripting, attachments are called Data Objects. Files can be added as attachments using the importDataObject( ) document method. The cName parameter, which is the name you give to the data object, is mandatory. When adding an attachment with the UI, the application names the data object the same as its file name, including the file extension. When the attachment is added with a script, the data object is named by the value of the cName parameter used in the script:
this.importDataObject("My Attachment");
The names of files in the attachments panel always display the file names of the document, including the file extension. This can get confusing when opening the files with a script (covered next). For example, if the file Blue.pdf in the screenshot above was added with the script above, the Data Object name will be My Attachment, not Blue.pdf.
When the script above is run in the console, a browse window opens to locate a file to attach. The process can be automated by including the cDIPath parameter (the system path to the file) and running the script from a privileged context (console, action, or trusted function in a folder level script). To get a list of all the attachments, run the following script in the console:
this.dataObjects
3. Drag & Drop
This by far the easiest way to attach files to a PDF. Simply open the attachments panel and drag the files into the panel. You can drag multiple files in at the same time. The files will automatically be named the same way as they are with the UI method described first.
Opening Attachments With JavaScript
The document method exportDataObject( ) extracts files and saves them. Like importDataObject, the cName parameter is mandatory. If the cName parameter is the only one used, the user will be prompted for a file location to extract to. The nLaunch parameter has three possible values that allow you to control whether the file is launched (re-opened):
0 The file will not be launched after it is saved.
1 The file will be launched after it is saved.
2 The file will launch after it is saved to a temporary file location. The user will not be prompted for a file location.
The temporary file location in 2 above is related to the file location of the PDF the file was attached to, so saving the file after making changes, then saving the PDF it is attached to, will save the changes in the attachment. The following command can be used to open an attachment:
this.exportDataObject({cName:"My Attachment", nLaunch:2});
If cName and nLaunch are the only two parameters used, the parameters must be named because there are two potential parameters between them in the parameter order. One is the cDIPath that can be used to specify a file path and save silently from a privileged context.
Putting It All Together
One of the reasons I prefer using attachments instead of portfolios is the ability to modify non-PDF files and save them inside the PDF. The main reason is the flexibility in customizing the “interface” (the PDF containing the attachments). This PDF can be made to look anyway you want it to. Here's a list of just some of the methods you can use to open the the attachments:
Links
Check boxes or radio buttons
Transparent buttons laid over text
List boxes
The transparent button option can be used in a PDF with a table of contents look. The buttons laid over the text would use mouse up actions to open the attachments. In all cases, the script to execute is the exportDataObject( ) with the nLaunch parameter value of 2 as shown in the last code block above.
Build A Clickable Table of Contents In Seconds
After you've created your PDF and have it looking the way want you want, and have all the files you are going to use for attachments in one folder, you can create a clickable table of contents that opens those files as attachments in seconds. (Make sure you name the files the way you want them to be named in your table of contents). Here are the steps.
Create a list box form field on the PDF and size it to accommodate a list of all the data object names in a list. (In the is example the name of the list box field is List Box). Check off "Commit select value immediately" in the options tab of the field properties.
Open the attachments panel of the PDF.
Select all the files and drag them into the attachments panel.
Run the following script in the console:
var aray=[]; for(var i=0;i<this.dataObjects.length;i++) {aray.push(this.dataObjects[i].name);} this.getField("List Box").setItems(aray);
The list box should now contain all of the attachment file names, which are also the data object names.
Enter the following script in the Selection Change tab of the list box field properties:
this.exportDataObject({cName:event.changeEx,nLaunch:2});
That's all there is to it. When the user makes a selection, the attachment will open. If the attachments are all PDFs and you want the focus to stay on the original PDF after an attachment is opened, simply add the following lines of code to the script above:
var pth=this.path;
app.openDoc(pth);
Enhanced Version
In the example above, suppose you don't want the file extensions to display in the list box. If you push arrays into the array that sets the items of the list box, the list box will contain display values, as well as export values. Removing the file extension from the display value and leaving it in the export value will not show the file extensions in the list box, but it will function the same. Assuming the only period in the file names is the one before the file extension, the following script would be used to set the list box items:
var aray=[];
for(var i=0;i<this.dataObjects.length;i++)
{
aray.push([this.dataObjects[i].name.split(".")[0],this.dataObjects[i].name]);
}
this.getField("List Box").setItems(aray);
You can verify it worked in the options tab of the list box properties by ensuring the export values contain the file extensions.