Accessibility

Table of Contents

Introducing Adobe AIR for Ajax developers

Leveraging native integration

The application I’ve described in the previous section now runs as a desktop application. It doesn't leverage any of the Adobe AIR APIs. Now imagine that you want the application to write to the local file system. The Adobe AIR API provides the File, FileStream, and FileMode classes to accomplish this task. Again, leveraging your existing web development skills, you can add just a few lines of JavaScript to utilize these classes and write data to the local disk (see fileio.html in the sample files folder).

// Create a reference to a place on disk to store the data
			  // Create a string of text to store in the file
			  // Create a stream for use in writing the data 
			  var file = air.File.desktopDirectory.resolvePath( 'hello.txt' );
			  var msg = 'Hello world, from AIR!';
			  var stream = new air.FileStream();
			  
            // Open the stream for writing
            // Write the name value to the file using system encoding
            // Close the stream 
            stream.open( file, air.FileMode.WRITE );
            stream.writeMultiByte( msg, air.File.systemCharset );
            stream.close();

Realistically, this data will likely come from some service endpoint as XML, using the XMLHttpRequest (XHR) class. Again, with Adobe AIR, developers are free of the traditional domain security limitations and their applications can request data from any endpoint. What if the remote server is down? What if the network cable is inoperative? These types of desktop deployment challenges are handled by the Adobe AIR network/service monitor class, see network.html and servicemonitor.swf in the sample files.

// Specify what URL to monitor
		    var endpoint = new air.URLRequest( SERVICE_URL );
            // Create the object to monitor the endpoint
            // Call a function when the network status changes
            // Start listening for a network change
            monitor = new air.URLMonitor( endpoint );
            monitor.addEventListener( air.StatusEvent.STATUS, doStatus );
            monitor.start();
            
            ...
            
            var xhr = null;
            
		    // The network is available
		    if( monitor.available )
		    {
		    // Create the object for the data request
		    xhr = new XMLHttpRequest();
  
		    // Listen for the various changes during the request
		    xhr.onreadystatechange = function()
		    {
		    var file = null;
		    var stream = null;
 
		    // When the data has been retrieved
		    if( xhr.readyState == 4 )
		    {
		    // Create a reference to a location on disk
		    file = air.File.desktopDirectory.resolvePath( LOCAL_FILE );
 
		    // Create the file IO stream
		    // Open the stream for writing
		    // Write the response data (text)
		    // Close the stream 
		    stream = new air.FileStream();
		    stream.open( file, air.FileMode.WRITE );
		    stream.writeMultiByte( xhr.responseText, air.File.systemCharset );
		    stream.close();
		    }
		    }
 
		    // Open the network connection and send the request
		    xhr.open( 'GET', DATA_URL, true );
		    xhr.send( null ); 
	    }

In the case that network connectivity cannot be achieved, perhaps the application could offer a means to drag and drop data directly. Although drag-and-drop inside the browser has been possible for a while, drag-and-drop that extends beyond the browser is among the core features of Adobe AIR. There's even support for the various types of data that might be dragged into (or out of) an application from the OS itself. In addition to text, this includes file lists, bitmap data, and URLs. If you’re following along, open dragdrop.html in the provided sample files folder.

// Called when a mouse drag gesture is over the application 
function doOver( e )
{
    // Check the types of data being dragged
    for( var t = 0; t < e.dataTransfer.types.length; t++ )
    {
        // Make sure there is a type you can handle 
        f( e.dataTransfer.types[t] == 'application/x-vnd.adobe.air.file-list' )
            {
            // Tell WebKit to avoid the default behavior (ignore)
            e.preventDefault();
            }
     }
}
// Called when a mouse gesture drops data on the application function doDrop( e )
{
    var data = null;
    var elem = null; 
    var file = null;
    var list = null;
    var stream = null;
	
    // Get the list of files that were dropped
    list = e.dataTransfer.getData( 'application/x-vnd.adobe.air.file-list' );
    // Iterate through the list of dropped files
    for( var f = 0; f < list.length; f++ )
    {
        // Create a new file IO stream
        // Open the current file in the iteration
        // Read the contents as text data into a variable
        // Close the stream
        stream = new air.FileStream();
        stream.open( list[f], air.FileMode.READ );
        data = stream.readMultiByte( stream.bytesAvailable, air.File.systemCharset );
        stream.close();
   
        // Create a new HTML DIV to hold the data
        // Put the data in the DIV and append it to the document
        elem = document.createElement( 'div' );
        elem.innerText = data;
        document.body.appendChild( elem );
    }
}

Now that the application can manage data through file IO, network service requests, and native drag-and-drop support, there might be a reason to add data storage that's a little more robust than CSV, XML, or plain text. The open source relational database SQLite is included as part of Adobe AIR and it offers high performance data storage and retrieval via ANSI SQL-92 complaint syntax (see feeds.db in the sample files). This not only includes support for text and numeric values, but also for binary data (BLOB). The code below is available in the provided sample files. Open database.html to see the entire file.

// Called when the document finishes loading 
function doLoad()
{
    var ship = air.File.applicationDirectory.resolvePath( DATABASE_FILE );
    var store = air.File.applicationStorageDirectory.resolvePath( DATABASE_FILE );


    // Put the database in a writable place first
    if( !store.exists)
    {
        ship.copyTo( store );
    }
   
    // INFO: air.trace( 'Database at: ' + store.nativePath ); 
   
    // Open a connection to the SQLite database
    db = new air.SQLConnection();
    db.addEventListener( air.SQLEvent.OPEN, doDbOpen );
    db.open( store, air.SQLMode.CREATE ); 

}

What you have now is a web application, developed using standard web development technologies, that has integrated desktop features. This relatively simple example takes on features that simply aren't possible in the web browser. Although it doesn't replace the browser itself, features such as file IO, network awareness, and native drag-and-drop support readily extend an existing web presence to the desktop.