9 Replies Latest reply on Mar 30, 2009 1:29 PM by Ari_Ugwu

    HTML Javascript talking to AIR

    xIconox
      My Adobe Air application has a web browser (htmlLoader) in it. This Browser is gonna be a program, that will walk you through some steps, and on the final page I would like to do 2 things.

      1) Print the webpage as a receipt
      2) Call a function letting the Air application know that the process is completed.

      THAT'S IT!

      When I google for the answer on how to do this, I get a lot of sandbox API, which seems like it's the right direction BUT it's not! They want me to have an iframe? How do I expose the methods in AIR?

      It seems like most examples are for talking to flash inside a webpage, rather than talking to the AIR application that is hosting the web page. Can someone please shed some light? I'm working with web developers and they need to know how to pass messages to my AIR container!

      Thanks in advance,
      -G

        • 1. Re: HTML Javascript talking to AIR
          Jeff Swartz Level 3
          Will you be developing your AIR file using SWF content as the root content (with an HTMLLoader object used to load the HTML)? Or will you be writing an AIR application written entirely in HTML and JavaScript?

          Is the HTML content loaded from HTML pages installed with your application? Or is it loaded from a remote URL?
          • 2. Re: HTML Javascript talking to AIR
            xIconox Level 1
            Answer 1) Developing in air using SWF content as the root content.

            Answer 2) Loaded from a remote URL

            btw, thank you for your time
            • 3. Re: HTML Javascript talking to AIR
              Joe ... Ward Level 4
              To allow the webpage to call a function defined in your ActionScript container, your container must set the window.parentSandboxBridge property of the HTML page to an object that has this function. The object can be defined in ActionScript or JavaScript.

              See http://help.adobe.com/en_US/AIR/1.5/devappsflex/WS5b3ccc516d4fbf351e63e3d118666ade46-7f08. html

              You only need an iframe when you need an HTML page that is part of your application to behave like it is part of the remote domain (to allow easier cross scripting).
              • 4. Re: HTML Javascript talking to AIR
                xIconox Level 1
                Joe, thank you for your time. I've made some progress, but I'm not out of the dark. The complication is that those 2 cases used in the cookbook are not the direction I need.

                the first is
                application -> non-application

                the second is
                non-application -> non-application

                and what I desire is
                non-application -> application

                Sounds easy, but I'm not sure I know the logic yet.

                As per your suggestion I've done the following:
                Created a non-application HTML page with the following link
                <a href="javascript:window.parentSandboxBridge.helloWorld();">Yo let's do this!</a>

                Created an object called TestBridge with a single public AS3 function of
                public function helloWorld():void
                {
                trace("IT FOUND ME");
                }

                I set the htmlLoader's window.parentSandboxBridge equal to a new global instance of TestBridge called myTest.

                As I understand it, that should be it! I run the application, it loads the page fine, with no errors, and when I click the link that runs the sandbox javascript Air traces the following
                "TypeError: Undefined value"

                Sooooooo, I've done everything... or so I think. What am I missing?
                • 5. Re: HTML Javascript talking to AIR
                  xIconox Level 1
                  Can anyone else elaborate on what I've done wrong, I'm not just waiting for Joe :)

                  *bump*
                  • 6. Re: HTML Javascript talking to AIR
                    Joe ... Ward Level 4
                    Hmm... I get the same error. Perhaps I'm wrong in thinking that you can bridge directly from ActionScript to JavaScript. I'll investigate and let you know.

                    In the meantime, you can use an intermediate HTML page to load the remote page and set up the bridge as follows:

                    MXML file (you could do the same in ActionScript, without Flex):
                    <?xml version="1.0" encoding="utf-8"?>
                    <mx:WindowedApplication xmlns:mx=" http://www.adobe.com/2006/mxml" layout="absolute" applicationComplete="init()">
                    <mx:Script>
                    <![CDATA[

                    private var testInterface:Object = new Object();

                    private function init():void
                    {
                    testInterface.helloWorld = this.helloWorld;
                    }

                    public function helloWorld():void
                    {
                    trace("IT FOUND ME!");
                    }

                    private function addBridgeObject():void
                    {
                    trace("Added bridge object");
                    html.domWindow.interfaceObject = testInterface;
                    }
                    ]]>
                    </mx:Script>
                    <mx:HTML id="html" location="app:/bridge.html" htmlDOMInitialize="addBridgeObject()" width="100%" height="100%"/>
                    </mx:WindowedApplication>

                    The application HTML file bridge.html (that sets up the bridge):
                    <html>
                    <head>
                    <script>

                    var addBridge = function(){
                    document.getElementById('child').contentWindow.parentSandboxBridge = interfaceObject;
                    window.runtime.trace('js bridge call');
                    }
                    </script>
                    </head>
                    <body onload='addBridge()'>
                    <iframe id='child' src='file:///C:/foo.html'></iframe>
                    </body>
                    </html>

                    The remote html file -- foo.html:
                    <html>
                    <body>
                    <a href="javascript:window.parentSandboxBridge.helloWorld();">Yo let's do this!</a>
                    </body>
                    </html>
                    • 7. Re: HTML Javascript talking to AIR
                      Jeff Swartz Level 3
                      You need not use the sandbox bridge. The ActionScript can map a JavaScript function to an ActionScript function, as in the following:

                      1. In the ActionScript:

                      html.htmlLoader.load(urlReq);
                      html.htmlLoader.addEventListener(Event.HTML_DOM_INITIALIZE, loaded);
                      function loaded(e:Event)
                      {
                      html.htmlLoader.window.foo = fooFun;
                      }
                      function fooFun():void
                      {
                      trace("Hello");
                      }

                      2. In the JavaScript:

                      <a onClick="foo()">Click me.</a>

                      Here's more information:

                      http://help.adobe.com/en_US/AIR/1.5/devappsflex/WS5b3ccc516d4fbf351e63e3d118666ade46-7ed5. html

                      Unfortunately, AIR does not support window.print(). You can, however, use the ActionScript PrintJob class to print the HTMLLoader.
                      • 8. Re: HTML Javascript talking to AIR
                        xIconox Level 1
                        swartz thank you so much. And the reason I'm doing this is exactly for the window.print :D

                        I learned a lot about sandboxing in this, but I'm glad that I don't need it for this process.

                        Thanx everyone.
                        -Gant
                        • 9. Re: HTML Javascript talking to AIR
                          Ari_Ugwu
                          Tutorial Link
                          I searched for an elegant print solution for awhile using only javascript. Ended up making my own.

                          What I came up with is a demo that shows how to use postMessage. This will allow you to communicate directly with the PDF. In the example I use it to post the contents of an input box into the PDF and fill a form field.

                          Here is a link in case it didn't come through above: http://www.drybydesign.com/2009/03/29/adobe-air-pdf-cross-scripting/

                          I believe the this will solve most print needs as it will allow you to harness the PDF interface. The code is light but largely undocumented. As the demo progresses and I get feedback I'll make it more robust. Love to know your thoughts. Leave a comment on my blog to show support!