Download as pdf or txt
Download as pdf or txt
You are on page 1of 9

10/20/2010 Cross-scripting PDF content in an Ad…

Adobe
Products Solutions Learning Help Downloads Company
Store
Adobe Store for home and home office
Education Store for students, educators, and staff
Business Store for small and medium businesses
Other ways to buy

Search Search
Info Sign in
My cart My shipments My support

Adobe Developer Connection / Adobe AIR Developer Center / AIR Quick Starts for
ActionScript developers /

Cross-scripting PDF content in an Adobe


AIR application
by Jeff Swartz

Modified
Jun 9, 2010

Comments (13)

(0 Ratings)

Requirements
Prerequisite knowledge
General experience of building applications with Flex Builder or the Flex SDK is suggested.
For more details on getting started with this Quick Start, refer to Building the Quick Start
sample applications with Flex.

User level
Intermediate

adobe.com/…/scripting_pdf.html 1/9
10/20/2010 Cross-scripting PDF content in an Ad…
Required products
Adobe AIR (Download trial)
Flash Builder (Download trial)
Flex (Download trial)

Sample files
PDFControlFlex.zip
PDFControlFlex.air

This Flex based PDF Control sample application loads a PDF file. You navigate through the
file using user interface provided by HTML (not by the embedded PDF renderer). The zoom
and navigation buttons are at the top of the application (see Figure 1).

The PDF Control sample application demonstrates the following features of working with
PDF content in Adobe AIR:

Adding PDF content to an AIR application


Using Acrobat 8 to add JavaScript to a PDF file
Using ActionScript in an AIR application to communicate with document-level
JavaScript in a PDF file

adobe.com/…/scripting_pdf.html 2/9
10/20/2010 Cross-scripting PDF content in an Ad…
Figure 1. This sample application enables you to load PDF files.

Note: This is a sample application provided, as is, for instructional purposes.

This sample application includes the following files:

PDFControlFlex.mxml: The main application file in MXML for Flex; includes the code
discussed in this article
PDFControlFlex-app.xml: The AIR application descriptor file
test.pdf: A sample PDF file loaded by the application
index.html: An HTML file loaded into the application
Sample AIR icon files

Important

The application descriptor file, PDFControlFlex-app.xml, uses the AIR 1.0 namespace. If you
are compiling the application using Flex Builder 3.0.2 or Flex SDK 3.2 or later, edit the file to
use the AIR 1.5 namespace:
xmlns="http://ns.adobe.com/air/application/1.5"

Otherwise, you will not be able to test or package the application.

Understanding the code

Note: This article does not describe all of the Flex components used in the MXML code for
the file. For more information, see the Flex 3 Language Reference.

The message handler JavaScript function in the PDF file

In document-level JavaScript in a PDF file, you can assign functions to the onMessage ,
onError, and onDisclose properties of the msgHandler property of the hostContainer object.
These functions define how the PDF file handles messages sent to it from the host container.

The test.pdf file, included with the sample files, includes the following document-level
JavaScript:
function myOnMessage(aMessage) { if (aMessage.length==1) { switch(aMessage[0])
{ case "ZoomIn": zoom *= 2; break; case "ZoomOut": zoom /= 2; break; case
"PageUp": pageNum--; break; case "PageDn": pageNum++; break; default:
app.alert("Unknown message: " + aMessage[0]); } } else { app.alert("Message
from hostContainer: \n" + aMessage); } } function
myOnDisclose(cURL,cDocumentURL) { return true; } function myOnError(error,
aMessage) { app.alert(error); } var msgHandlerObject = new Object();
msgHandlerObject.onMessage = myOnMessage; msgHandlerObject.onError = myOnError;
msgHandlerObject.onDisclose = myOnDisclose; this.hostContainer.messageHandler =
msgHandlerObject;

This code defines functions for handling incoming messages. It sets these functions as the
onMessage , onError , and onDisclose properties of an object, msgHandlerObject . The code
assigns the msgHandlerObject object to the msgHandler property of the hostContainer
object. The myOnDisclose() function checks the first string in the incoming message array,
and takes the appropriate action. For example, if the string is "ZoomIn" , the code sets a
PDF JavaScript property to zoom the page in: zoom *= 2.

adobe.com/…/scripting_pdf.html 3/9
10/20/2010 Cross-scripting PDF content in an Ad…
This example application shows basic page navigation and display scale factor. Full details
on other JavaScript extensions for Adobe Acrobat are provided at the Adobe Acrobat
Developer Center.

Adding document-level JavaScript to a PDF file

Follow these steps:

1. Create a PDF document named test.pdf and save it to the project directory for your
application.
2. Open the PDF in Acrobat 8.
3. On the Advanced menu, select Document Processing > Document JavaScripts.
4. In the JavaScript Functions dialog box, type myOnMessage as the Script Name, and
then click the Add button.
5. In the JavaScript Editor window, edit the text to match the following, and then click the
OK button.
function myOnMessage(aMessage) { if (aMessage.length==1) { switch(aMessage[0])
{ case "ZoomIn": zoom *= 2; break; case "ZoomOut": zoom /= 2; break; case
"PageUp": pageNum--; break; case "PageDn": pageNum++; break; default:
app.alert("Unknown message: " + aMessage[0]); } } else { app.alert("Message
from hostContainer: \n" + aMessage); } } function
myOnDisclose(cURL,cDocumentURL) { return true; } function myOnError(error,
aMessage) { app.alert(error); } var msgHandlerObject = new Object();
msgHandlerObject.onMessage = myOnMessage; msgHandlerObject.onError = myOnError;
msgHandlerObject.onDisclose = myOnDisclose; this.hostContainer.messageHandler =
msgHandlerObject;

For a description of this code, see the previous section.

6. Close the JavaScript Functions dialog box.


7. Select the File > Document Properties command.
8. In the Document Properties dialog box, select the following options:
Navigation tab: Page Only
Page layout: Single Page
Maginfication: Default
Open to Page: 1
Hide menu bar: selected
Hide tool bars: selected
Hide window controls: selected
9. Save the PDF document to your project directory, and name it test.pdf.

Loading the PDF content into the AIR application

AIR applications can render PDF content inside an HTMLLoader object. The Flex HTML
component is a wrapper for an HTMLLoader object. The second-to-last line of the MXML
code for the sample application is the following:
<mx:HTML id="pdfHtml" location="test.html" width="100%" height="100%" />

It loads an HTML page included with the application: test.html. In turn, the test.html page
loads the PDF content, which is also included with the application: test.pdf. The following is
the code of the HTML page:
<html> <body> <object id="PDFObj" data="test.pdf" type="application/pdf"
width="100%" height="100%"/> </body> </html>

adobe.com/…/scripting_pdf.html 4/9
10/20/2010 Cross-scripting PDF content in an Ad…

Communicating with the JavaScript in the PDF file

The MXML code for the sample application defines four Button components:
<mx:Label text="Zoom:" width="75"/> <mx:Button id="btn1" label="+"
click="sendMessage('ZoomIn')" width="35" enabled="false"/> <mx:Button id="btn2"
label="-" click="sendMessage('ZoomOut')" width="35" enabled="false"/> <mx:Label
text="Navigate:" width="75"/> <mx:Button id="btn3" label="&lt;"
click="sendMessage('PageUp')" width="35"enabled="false"/> <mx:Button id="btn4"
label=">" click="sendMessage('PageDn')" width="35" enabled="false"/>

These buttons are disabled until the DOM the HTML component has initialized. The
application calls the init() function (defined in the MXML code) is called when the
applicationComplete event is dispatched:

private function init():void { fixPDFBug();


pdfHtml.htmlLoader.addEventListener(Event.HTML_DOM_INITIALIZE, htmlLoaded); }
private function fixPDFBug():void { var pdfFile:File =
File.applicationDirectory.resolvePath(pdfHtml.location); pdfFile = new
File(pdfFile.nativePath); var fileURL:String = pdfFile.url; pdfHtml.location =
fileURL; } private function htmlLoaded(event:Event):void { btn1.enabled = true;
btn2.enabled = true; btn3.enabled = true; btn4.enabled = true; }

Note: The fixPDFBug() method fixes a bug in some versions of Acrobat. In these versions of
Acrobat, the HTML content does not dispatch a complete event if the PDF content uses an
app: URL. The code reloads the HTML page (and the PDF it contains), using a file: URL
instead of an app: URL.

When the user clicks any one of the Button components, the click event handler calls the
sendMessage() method. For example, clicking the first button causes the following code to
execute:
sendMessage('ZoomIn')

The sendMessage() method sets an object, pdfObj, to the PDFObj element in the HTML page.
This is the object in the HTML DOM containing the embedded PDF content. You can send a
message to the embedded PDF object by calling its postMessage() method. The
postMessage() method takes an array of message strings as a parameter:

private function sendMessage(message:String):void { try { var pdfObj:Object =


pdfHtml.htmlLoader.window.document.getElementById("PDFObj");
pdfObj.postMessage([message]); } catch (error:Error) { trace( "Error: " +
error.name + "\nError message: " + error.message); } }

The document-level JavaScript in the PDF file has a hostContainer.messageHandler object


defined. This object determines how to processes the incoming message. (For details, see
the section "The message handler JavaScript function in the PDF file" above.) In this
application, the PDF content navigates or magnifies.

Comments (13)
Comments

Ari UgwuMarch 30, 2009

I did javascript version of this for those who don't use flex. I also found I had to add a
few lines of additional code to get it to work. Here is the link:
adobe.com/…/scripting_pdf.html 5/9
10/20/2010 Cross-scripting PDF content in an Ad…
http://www.drybydesign.com/2009/03/29/adobe-air-pdf-cross-scripting/

Jeff Swartz(Administrator)March 30, 2009

Thanks, Ari. I like your example.

I also wrote an HTML-based version of this here:

http://www.adobe.com/devnet/air/ajax/quickstart/scripting_pdf.html

There are more HTML-based "quick start" example applications here:

http://www.adobe.com/devnet/air/ajax/quickstart/index.html

李鑫April 1, 2009

If i want print the pdf , what message do i send?


sendMessage('Print')"

marcbcAugust 22, 2009

Hi,
I'd like to implement a feature like the one described in this article, but I'd like the user
being able to load his/her own PDF documents, without being generated in any special
way in Acrobat.
Is it possible somehow? I was thinking if it would be possible to inject these scripts for
handling/dispatching events from and to the PDF once the document is loaded in the
AIR application...

any idea will be helpful!

thanks,

Marc Baiges Camprubí

marcbcAugust 23, 2009

Someone in the flexcoders group pointed me to this post:


http://gonzalo.huerta.cl/?p=13

so it seems that is possible with that patch over AlivePDF and that the self library will
include something similar in the 0.1.5 release :-)
http://alivepdf.bytearray.org/?p=150

let's try it!

Marc Baiges Camprubí

marcbcAugust 26, 2009

just realized this solution is not valid since I can only add the required scripts when
creating the PDF document with AlivePDF, but I'm not able to load existing PDF's and
modify them...
Maybe with some Java-PDF library and Merapi? If anyone has any advice...

th k
adobe.com/…/scripting_pdf.html 6/9
10/20/2010 Cross-scripting PDF content in an Ad…
thanks,

Marc Baiges Camprubí

jony jonyAugust 26, 2009

Hi...

Do you know how can I display my PDF document when I have my application in
Fullscreen mode?

If I don't use fullscreen mode, I don't have any problems... but... otherwise my PDF
doesn't open and HTML place appears tottaly dark.

Thanks.

Regards.

marcbcAugust 28, 2009

Hi Jony,
for the current AIR version, it's a "known limitation", as described in
http://help.adobe.com/en_US/AIR/1.5/devappsflex/WS5b3ccc516d4fbf351e63e3d118666ade46-
7eb4.html#WS5b3ccc516d4fbf351e63e3d118666ade46-7cfe:

================================================
Known limitations for PDF content in AIR
PDF content in Adobe AIR has the following limitations:

PDF content does not display in a window (a NativeWindow object) that is transparent
(where the transparent property is set to true).
The display order of a PDF file operates differently than other display objects in an AIR
application. Although PDF content clips correctly according to HTML display order, it
will always sit on top of content in the AIR application's display order.
PDF content does not display in a window that is in full-screen mode (when the
displayState property of the Stage is set to StageDisplayState.FULL_SCREEN or
StageDisplayState.FULL_SCREEN_INTERACTIVE).
If certain visual properties of an HTMLLoader object that contains a PDF document are
changed, the PDF document will become invisible. These properties include the filters,
alpha, rotation, and scaling properties. Changing thse renders the PDF file invisible
until the properties are reset. This is also true if you change these properties of display
object containers that contain the HTMLLoader object.
PDF content is visible only when the scaleMode property of the Stage object of the
NativeWindow object containing the PDF content is set to
StageScaleMode.NO_SCALE. When it is set to any other value, the PDF content is not
visible.
Clicking links to content within the PDF file update the scroll position of the PDF
content. Clicking links to content outside the PDF file redirect the HTMLLoader object
that contains the PDF (even if the target of a link is a new window).
PDF commenting workflows do not function in AIR.
================================================

Let's hope the PDF suppport is improved in future versions!

adobe.com/…/scripting_pdf.html 7/9
10/20/2010 Cross-scripting PDF content in an Ad…

best,

Marc Baiges Camprubí

Anatole TartakovskyOctober 2, 2009

Marc,
Seems like the example is not working on the latest AIR/Snow Leopard combo? is
there fix available?
Here are the details:
Process: PDF Control (Flex) [1536]
Path: /Applications/Adobe/AIR Examples/PDF Control
(Flex).app/Contents/MacOS/PDF Control (Flex)
Identifier: PDFControlFlex.419D633A757E8B26DD2BDB301927BA7BA7490F38.1
Version: 1.0 (???)
Code Type: X86 (Native)
Parent Process: launchd [169]

Date/Time: 2009-10-02 11:18:42.944 -0400


OS Version: Mac OS X 10.6.1 (10B504)
Report Version: 6

Interval Since Last Report: 32998 sec


Crashes Since Last Report: 6
Per-App Interval Since Last Report: 2 sec
Per-App Crashes Since Last Report: 1
Anonymous UUID: 14BC1396-E2C1-4990-B211-1CC84F4F8F98

Exception Type: EXC_BAD_ACCESS (SIGBUS)


Exception Codes: KERN_PROTECTION_FAILURE at 0x000000000000a7d8
Crashed Thread: 0 Dispatch queue: com.apple.main-thread

Thread 0 Crashed: Dispatch queue: com.apple.main-thread


0 libSystem.B.dylib 0x901a33c8 _qsort + 1201
1 AdobeACE 0x7
Thank you
Anatole

randyfongNovember 3, 2009

After compiling the source code in this article, a PDF is not displaying using AIR 1.5.
The source was compiled using Flex 3.0.2. The window and other flex items display
fine. It's just the PDF that does not display.

The runtime version from this article runs fine and display's a PDF.

I've changed the namespace to xmlns="http://ns.adobe.com/air/application/1.5" in the


app xml - so that is not the issue.

I have other AIR/PDF apps that aren't working now either using AIR 1.5. They were
working fine just a week or two ago.

Platform tested on the Windows 64bit Vista Ultimate OS.


adobe.com/…/scripting_pdf.html 8/9
10/20/2010 Cross-scripting PDF content in an Ad…

Prakash PhilipDecember 11, 2009

Hi Jeff,

I implemented your code and its working very fine. I just added one rotate button to this
code. but that is not working. this code i used for this rotation.
case "Turning":
if (this.numPages > 0)
{
this.setPageRotations(nStart = 0,nEnd= this.numPages - 1,nRotate = 90)
}
break;
any idea will be helpful!

steven@vervorm.beMarch 3, 2010

Hi,

Nice Article, Installed the AIR application and that worked.

I would like to know if the pdf can talk back to the AIR application. If yes, how can I do
that. Because I don't have a clue.

I'm also trying to redo your example with Flash CS4. With no success. I don't see what
I'm doing wrong. The pdf loads and even trigger a javascript alert from within the pdf.
But the app doesn't seem to trigger the javascript in the pdf. The code is exactly the
same as in the flex application.
Please help.

regards,
Steven

dccwilliamsDecember 7, 2010

Unless I'm going crazy, I can't find a way to download PDFControlFlex.zip. In fact, I can't
download any of the Flex quick start bundles, because they are not links! Seriously you
guys at Adobe, when your customers are trying to compete with the likes Silverlight and
the myriad of documentation and examples they provide, you need to at least make
sure they can access the quick starts!

Please sign in to improve or rate the content.


Choose your region
Security Contact Adobe Report piracy EULAs Permissions and trademarks Careers

Copyright © 2010 Adobe Systems Incorporated. All rights reserved.

Use of this website signifies your agreement to the Terms of Use and Online Privacy Policy
(updated 07-14-2009).

adobe.com/…/scripting_pdf.html 9/9

You might also like