Index: CKEditor/branches/features/adobeair/_samples/adobeair/application.xml
===================================================================
--- CKEditor/branches/features/adobeair/_samples/adobeair/application.xml	(revision 4294)
+++ CKEditor/branches/features/adobeair/_samples/adobeair/application.xml	(revision 4294)
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8" ?>
+<application xmlns="http://ns.adobe.com/air/application/1.0">
+	<id>net.fckeditor.air.samples.sample01</id>
+	<name>CKEditor Sample Application 1.0</name>
+	<version>1.0</version>
+	<filename>CKEditor AIR Sample</filename>
+	<description>This is a sample AIR application of CKEditor.</description>
+	<copyright>Copyright (C) 2003-2009 Frederico Caldeira Knabben</copyright>
+	<initialWindow>
+		<content>_samples/replacebyclass.html</content>
+		<title>Replace Textareas by Class Name - CKEditor Sample</title>
+		<systemChrome>standard</systemChrome>
+		<transparent>false</transparent>
+		<visible>true</visible>
+		<minimizable>true</minimizable>
+		<maximizable>true</maximizable>
+		<resizable>true</resizable>
+		<x>100</x>
+		<y>80</y>
+		<width>820</width>
+		<height>600</height>
+		<minSize>600 400</minSize>
+	</initialWindow>
+	<installFolder>CKEditor/AIR Samples/ReplaceByClassName</installFolder>
+	<programMenuFolder>CKEditor/AIR Samples</programMenuFolder>
+	<icon>
+		<image16x16>_samples/adobeair/icons/16.png</image16x16>
+		<image32x32>_samples/adobeair/icons/32.png</image32x32>
+		<image48x48>_samples/adobeair/icons/48.png</image48x48>
+		<image128x128>_samples/adobeair/icons/128.png</image128x128>
+	</icon>
+	<customUpdateUI>false</customUpdateUI>
+	<allowBrowserInvocation>false</allowBrowserInvocation>
+</application>
Index: CKEditor/branches/features/adobeair/_samples/adobeair/package.bat
===================================================================
--- CKEditor/branches/features/adobeair/_samples/adobeair/package.bat	(revision 4294)
+++ CKEditor/branches/features/adobeair/_samples/adobeair/package.bat	(revision 4294)
@@ -0,0 +1,26 @@
+@ECHO OFF
+
+::
+:: FCKeditor - The text editor for Internet - http://www.fckeditor.net
+:: Copyright (C) 2003-2009 Frederico Caldeira Knabben
+::
+:: == BEGIN LICENSE ==
+::
+:: Licensed under the terms of any of the following licenses at your
+:: choice:
+::
+::  - GNU General Public License Version 2 or later (the "GPL")
+::    http://www.gnu.org/licenses/gpl.html
+::
+::  - GNU Lesser General Public License Version 2.1 or later (the "LGPL")
+::    http://www.gnu.org/licenses/lgpl.html
+::
+::  - Mozilla Public License Version 1.1 or later (the "MPL")
+::    http://www.mozilla.org/MPL/MPL-1.1.html
+::
+:: == END LICENSE ==
+::
+
+:: adt -package SIGNING_OPTIONS air_file app_xml [file_or_dir | -C dir file_or_dir | -e file dir ...] ...
+
+adt -package -storetype pkcs12 -keystore sample01_cert.pfx -storepass 123abc FCKeditor.air application.xml -C ../../ .
Index: CKEditor/branches/features/adobeair/_samples/adobeair/run.bat
===================================================================
--- CKEditor/branches/features/adobeair/_samples/adobeair/run.bat	(revision 4294)
+++ CKEditor/branches/features/adobeair/_samples/adobeair/run.bat	(revision 4294)
@@ -0,0 +1,26 @@
+@ECHO OFF
+
+::
+:: FCKeditor - The text editor for Internet - http://www.fckeditor.net
+:: Copyright (C) 2003-2009 Frederico Caldeira Knabben
+::
+:: == BEGIN LICENSE ==
+::
+:: Licensed under the terms of any of the following licenses at your
+:: choice:
+::
+::  - GNU General Public License Version 2 or later (the "GPL")
+::    http://www.gnu.org/licenses/gpl.html
+::
+::  - GNU Lesser General Public License Version 2.1 or later (the "LGPL")
+::    http://www.gnu.org/licenses/lgpl.html
+::
+::  - Mozilla Public License Version 1.1 or later (the "MPL")
+::    http://www.mozilla.org/MPL/MPL-1.1.html
+::
+:: == END LICENSE ==
+::
+
+:: adl [-runtime runtime-directory] [-pubId publisher-id] [-nodebug] application.xml [rootdirectory] [-- arguments]
+
+adl application.xml ../../
Index: CKEditor/branches/features/adobeair/_source/core/ckeditor_base.js
===================================================================
--- CKEditor/branches/features/adobeair/_source/core/ckeditor_base.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/_source/core/ckeditor_base.js	(revision 4294)
@@ -13,5 +13,5 @@
 // ckeditor_source.js and ckeditor_basic_source.js files.
 
-// if(!window.CKEDITOR)window.CKEDITOR=(function(){var a={timestamp:'',version:'%VERSION%',rev:'%REV%',_:{},status:'unloaded',basePath:(function(){var d=window.CKEDITOR_BASEPATH||'';if(!d){var e=document.getElementsByTagName('script');for(var f=0;f<e.length;f++){var g=e[f].src.match(/(^|.*[\\\/])ckeditor(?:_basic)?(?:_source)?.js(?:\?.*)?$/i);if(g){d=g[1];break;}}}if(d.indexOf('://')==-1)if(d.indexOf('/')===0)d=location.href.match(/^.*?:\/\/[^\/]*/)[0]+d;else d=location.href.match(/^[^\?]*\/(?:)/)[0]+d;return d;})(),getUrl:function(d){if(d.indexOf('://')==-1&&d.indexOf('/')!==0)d=this.basePath+d;if(this.timestamp&&d.charAt(d.length-1)!='/')d+=(d.indexOf('?')>=0?'&':'?')+('t=')+this.timestamp;return d;}},b=window.CKEDITOR_GETURL;if(b){var c=a.getUrl;a.getUrl=function(d){return b.call(a,d)||c.call(a,d);};}return a;})();
+// if(!window.CKEDITOR)window.CKEDITOR=(function(){var a={timestamp:'',version:'%VERSION%',rev:'%REV%',_:{},status:'unloaded',basePath:(function(){var d=window.CKEDITOR_BASEPATH||'';if(!d){var e=document.getElementsByTagName('script');for(var f=0;f<e.length;f++){var g=e[f].src.match(/(^|.*[\\\/])ckeditor(?:_basic)?(?:_source)?.js(?:\?.*)?$/i);if(g){d=g[1];break;}}}if(d.indexOf(':/')==-1)if(d.indexOf('/')===0)d=location.href.match(/^.*?:\/\/[^\/]*/)[0]+d;else d=location.href.match(/^[^\?]*\/(?:)/)[0]+d;return d;})(),getUrl:function(d){if(d.indexOf(':/')==-1&&d.indexOf('/')!==0)d=this.basePath+d;if(this.timestamp&&d.charAt(d.length-1)!='/')d+=(d.indexOf('?')>=0?'&':'?')+('t=')+this.timestamp;return d;}},b=window.CKEDITOR_GETURL;if(b){var c=a.getUrl;a.getUrl=function(d){return b.call(a,d)||c.call(a,d);};}return a;})();
 
 // #### Raw code
@@ -127,5 +127,5 @@
 				// In IE (only) the script.src string is the raw valued entered in the
 				// HTML. Other browsers return the full resolved URL instead.
-				if ( path.indexOf('://') == -1 )
+				if ( path.indexOf(':/') == -1 )
 				{
 					// Absolute path.
@@ -163,5 +163,5 @@
 			{
 				// If this is not a full or absolute path.
-				if ( resource.indexOf('://') == -1 && resource.indexOf( '/' ) !== 0 )
+				if ( resource.indexOf(':/') == -1 && resource.indexOf( '/' ) !== 0 )
 					resource = this.basePath + resource;
 
Index: CKEditor/branches/features/adobeair/_source/core/config.js
===================================================================
--- CKEditor/branches/features/adobeair/_source/core/config.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/_source/core/config.js	(revision 4294)
@@ -197,5 +197,5 @@
 	 * @example
 	 */
-	plugins : 'about,basicstyles,blockquote,button,clipboard,colorbutton,colordialog,contextmenu,elementspath,enterkey,entities,filebrowser,find,flash,font,format,forms,horizontalrule,htmldataprocessor,image,indent,justify,keystrokes,link,list,maximize,newpage,pagebreak,pastefromword,pastetext,popup,preview,print,removeformat,resize,save,scayt,smiley,showblocks,sourcearea,stylescombo,table,tabletools,specialchar,tab,templates,toolbar,undo,wysiwygarea,wsc',
+	plugins : 'about,adobeair,basicstyles,blockquote,button,clipboard,colorbutton,colordialog,contextmenu,elementspath,enterkey,entities,filebrowser,find,flash,font,format,forms,horizontalrule,htmldataprocessor,image,indent,justify,keystrokes,link,list,maximize,newpage,pagebreak,pastefromword,pastetext,popup,preview,print,removeformat,resize,save,scayt,smiley,showblocks,sourcearea,stylescombo,table,tabletools,specialchar,tab,templates,toolbar,undo,wysiwygarea,wsc',
 
 	/**
Index: CKEditor/branches/features/adobeair/_source/core/dom/document.js
===================================================================
--- CKEditor/branches/features/adobeair/_source/core/dom/document.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/_source/core/dom/document.js	(revision 4294)
@@ -1,3 +1,3 @@
-﻿/*
+/*
 Copyright (c) 2003-2009, CKSource - Frederico Knabben. All rights reserved.
 For licensing, see LICENSE.html or http://ckeditor.com/license
@@ -207,4 +207,61 @@
 					return win;
 				})();
+		},
+
+		write : function( html )
+		{
+			if( !CKEDITOR.env.air )
+			{
+				this.$.open();
+				this.$.write( html );
+				this.$.close();
+			}
+			else
+			{
+				var doc = this;
+				// Grab all the <link> and <style> tags.
+				var stylesHtml = '';
+				html.replace( /<style[^>]*>[\s\S]*<\/style>|<link[^>]*?>/gi, function( match )
+				{
+					stylesHtml += match;
+				} );
+
+				if ( stylesHtml )
+				{
+					// Inject the <head> HTML inside a <div>.
+					// Do that before getDocumentHead because WebKit moves
+					// <link css> elements to the <head> at this point.
+					var div = new CKEDITOR.dom.element( 'div', doc );
+					div.setHtml( stylesHtml );
+					var getDocumentHead = function( doc )
+					{
+						var head ;
+						var heads = doc.getElementsByTagName( 'head' ) ;
+
+						if( heads && heads[0] )
+							head = heads[0] ;
+						else
+						{
+							head = doc.createElement( 'head' ) ;
+							doc.documentElement.insertBefore( head, doc.documentElement.firstChild ) ;
+						}
+
+						return head ;
+					} ;
+
+					// Move the <div> nodes to <head>.
+					div.moveChildren( new CKEDITOR.dom.element( getDocumentHead( doc.$ ) ) ) ;
+				}
+
+				var bodyMatch = html.match( /<body[^>]*>([\s\S]*)<\/body>/i ),
+					bodyContent = bodyMatch && bodyMatch[ 1 ],
+					body = bodyMatch && CKEDITOR.htmlParser.fragment.fromHtml( bodyMatch[ 0 ] ).children[ 0 ],
+					bodyAttrs = body.attributes,
+					docBody = doc.getBody();
+
+				docBody.setHtml( bodyContent );
+				if( bodyAttrs )
+					docBody.setAttributes( bodyAttrs );
+			}
 		}
 	});
Index: CKEditor/branches/features/adobeair/_source/core/loader.js
===================================================================
--- CKEditor/branches/features/adobeair/_source/core/loader.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/_source/core/loader.js	(revision 4294)
@@ -94,5 +94,5 @@
 			// In IE (only) the script.src string is the raw valued entered in the
 			// HTML. Other browsers return the full resolved URL instead.
-			if ( path.indexOf('://') == -1 )
+			if ( path.indexOf(':/') == -1 )
 			{
 				// Absolute path.
Index: CKEditor/branches/features/adobeair/_source/plugins/adobeair/plugin.js
===================================================================
--- CKEditor/branches/features/adobeair/_source/plugins/adobeair/plugin.js	(revision 4294)
+++ CKEditor/branches/features/adobeair/_source/plugins/adobeair/plugin.js	(revision 4294)
@@ -0,0 +1,76 @@
+/*
+Copyright (c) 2003-2009, CKSource - Frederico Knabben. All rights reserved.
+For licensing, see LICENSE.html or http://ckeditor.com/license
+*/
+
+CKEDITOR.plugins.add( 'adobeair',
+{
+	init : function( editor )
+	{
+		if( CKEDITOR.env.air )
+			editor.on( 'uiReady', function()
+			{
+				( function ( container, eventNameList )
+				{
+					for ( var i = 0; i < eventNameList.length; i++ )
+					{
+						( function( eventName ){
+
+							var targetList =
+								 container.eachChildWithAttribute( 'on'+ eventName, function( item )
+							{
+								item.on( eventName, function( evt )
+								{
+									var inlineEventHandler = item.getAttribute( 'on' + eventName ),
+										callFunc = /callFunction\(([^)]+)\)/.exec( inlineEventHandler ),
+										callFuncArgs = callFunc && callFunc[ 1 ].split( ',' ),
+										preventDefault = /return false;/.test( inlineEventHandler );
+
+									if ( callFuncArgs )
+									{
+										var nums = callFuncArgs.length,
+											argName;
+										for ( var i = 0; i < nums; i++ )
+										{
+											switch( argName = CKEDITOR.tools.trim( callFuncArgs[ i ] ) )
+											{
+												case 'this' :
+													callFuncArgs[ i ] = item.$;
+													break;
+												case 'event' :
+													callFuncArgs[ i ] = evt.data.$;
+													break;
+												case 'null' :
+													callFuncArgs [ i ] = null;
+													break;
+											}
+										}
+
+										CKEDITOR.tools.callFunction.apply( window, callFuncArgs );
+									}
+
+									if( preventDefault )
+										evt.data.preventDefault();
+
+								} );
+							} );
+
+						} )( eventNameList[ i ] );
+					}
+				} )( editor.container, [ 'click', 'keydown', 'mousedown', 'keypress' ] );
+			} );
+	}
+});
+
+CKEDITOR.dom.element.prototype.eachChildWithAttribute = function( name, processor )
+{
+	var children = this.getElementsByTag( '*' ),
+		count = children.count(),
+		child;
+	for ( var i = 0; i < count; i++ )
+	{
+		child = children.getItem( i );
+		if( child.hasAttribute( name ) )
+			processor( child );
+	}
+};
Index: CKEditor/branches/features/adobeair/_source/plugins/panel/plugin.js
===================================================================
--- CKEditor/branches/features/adobeair/_source/plugins/panel/plugin.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/_source/plugins/panel/plugin.js	(revision 4294)
@@ -135,6 +135,4 @@
 					langCode = parentDiv.getParent().getAttribute( 'lang' ),
 					doc = iframe.getFrameDocument();
-				// Initialize the IFRAME document body.
-				doc.$.open();
 
 				// Support for custom document.domain in IE.
@@ -149,5 +147,5 @@
 					}, this ) );
 
-				doc.$.write(
+				doc.write(
 					'<!DOCTYPE html>' +
 					'<html dir="' + dir + '" class="' + className + '_container" lang="' + langCode + '">' +
@@ -163,5 +161,4 @@
 						'<link type="text/css" rel=stylesheet href="' + this.css.join( '"><link type="text/css" rel="stylesheet" href="' ) + '">' +
 					'<\/html>' );
-				doc.$.close();
 
 				var win = doc.getWindow();
@@ -187,4 +184,7 @@
 
 				holder = doc.getBody();
+
+				if( CKEDITOR.env.air )
+					CKEDITOR.tools.callFunction( onLoad );
 			}
 			else
Index: CKEditor/branches/features/adobeair/_source/plugins/wysiwygarea/plugin.js
===================================================================
--- CKEditor/branches/features/adobeair/_source/plugins/wysiwygarea/plugin.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/_source/plugins/wysiwygarea/plugin.js	(revision 4294)
@@ -274,5 +274,5 @@
 						if ( CKEDITOR.env.gecko )
 						{
-							// Double checking the iframe will be loaded properly(#4058).
+						// Double checking the iframe will be loaded properly(#4058).
 							iframe.on( 'load', function( ev )
 							{
@@ -345,5 +345,6 @@
 						// Remove this script from the DOM.
 						var script = domDocument.getElementById( "cke_actscrpt" );
-						script.parentNode.removeChild( script );
+						if( script )
+							script.parentNode.removeChild( script );
 
 						delete CKEDITOR._[ 'contentDomReady' + editor.name ];
@@ -426,4 +427,13 @@
 						}
 
+						if( CKEDITOR.env.air )
+						{
+							//prevent clicking on hyperlinks and navigating away
+							domDocument.$.addEventListener( 'click', function( ev )
+								{
+									ev.preventDefault() ;
+									ev.stopPropagation() ;
+								}, true ) ;
+						}
 						var focusTarget = ( CKEDITOR.env.ie || CKEDITOR.env.webkit ) ?
 								domWindow : domDocument;
@@ -534,5 +544,5 @@
 									'</body>' +
 									'</html>' +
-									activationScript;
+									( !CKEDITOR.env.air ? activationScript : '' );
 
 								window[ '_cke_htmlToLoad_' + editor.name ] = data;
@@ -541,11 +551,12 @@
 
 								// Opera must use the old method for loading contents.
-								if ( CKEDITOR.env.opera )
-								{
-									var doc = iframe.$.contentWindow.document;
-									doc.open();
+								if ( CKEDITOR.env.opera || CKEDITOR.env.air )
+								{
+									var doc = new CKEDITOR.dom.document( iframe.$.contentWindow.document );
 									doc.write( data );
-									doc.close();
 								}
+
+								if( CKEDITOR.env.air )
+									contentDomReady( iframe.$.contentWindow );
 							},
 
Index: CKEditor/branches/features/adobeair/ckeditor_basic_source.js
===================================================================
--- CKEditor/branches/features/adobeair/ckeditor_basic_source.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/ckeditor_basic_source.js	(revision 4294)
@@ -6,5 +6,5 @@
 // Compressed version of core/ckeditor_base.js. See original for instructions.
 /*jsl:ignore*/
-if(!window.CKEDITOR)window.CKEDITOR=(function(){var a={timestamp:'',version:'%VERSION%',revision:'%REV%',_:{},status:'unloaded',basePath:(function(){var d=window.CKEDITOR_BASEPATH||'';if(!d){var e=document.getElementsByTagName('script');for(var f=0;f<e.length;f++){var g=e[f].src.match(/(^|.*[\\\/])ckeditor(?:_basic)?(?:_source)?.js(?:\?.*)?$/i);if(g){d=g[1];break;}}}if(d.indexOf('://')==-1)if(d.indexOf('/')===0)d=location.href.match(/^.*?:\/\/[^\/]*/)[0]+d;else d=location.href.match(/^[^\?]*\/(?:)/)[0]+d;return d;})(),getUrl:function(d){if(d.indexOf('://')==-1&&d.indexOf('/')!==0)d=this.basePath+d;if(this.timestamp&&d.charAt(d.length-1)!='/')d+=(d.indexOf('?')>=0?'&':'?')+('t=')+this.timestamp;return d;}},b=window.CKEDITOR_GETURL;if(b){var c=a.getUrl;a.getUrl=function(d){return b.call(a,d)||c.call(a,d);};}return a;})();
+if(!window.CKEDITOR)window.CKEDITOR=(function(){var a={timestamp:'',version:'%VERSION%',revision:'%REV%',_:{},status:'unloaded',basePath:(function(){var d=window.CKEDITOR_BASEPATH||'';if(!d){var e=document.getElementsByTagName('script');for(var f=0;f<e.length;f++){var g=e[f].src.match(/(^|.*[\\\/])ckeditor(?:_basic)?(?:_source)?.js(?:\?.*)?$/i);if(g){d=g[1];break;}}}if(d.indexOf(':/')==-1)if(d.indexOf('/')===0)d=location.href.match(/^.*?:\/\/[^\/]*/)[0]+d;else d=location.href.match(/^[^\?]*\/(?:)/)[0]+d;return d;})(),getUrl:function(d){if(d.indexOf(':/')==-1&&d.indexOf('/')!==0)d=this.basePath+d;if(this.timestamp&&d.charAt(d.length-1)!='/')d+=(d.indexOf('?')>=0?'&':'?')+('t=')+this.timestamp;return d;}},b=window.CKEDITOR_GETURL;if(b){var c=a.getUrl;a.getUrl=function(d){return b.call(a,d)||c.call(a,d);};}return a;})();
 /*jsl:end*/
 
Index: CKEditor/branches/features/adobeair/ckeditor_source.js
===================================================================
--- CKEditor/branches/features/adobeair/ckeditor_source.js	(revision 4293)
+++ CKEditor/branches/features/adobeair/ckeditor_source.js	(revision 4294)
@@ -6,5 +6,5 @@
 // Compressed version of core/ckeditor_base.js. See original for instructions.
 /*jsl:ignore*/
-if(!window.CKEDITOR)window.CKEDITOR=(function(){var a={timestamp:'',version:'%VERSION%',revision:'%REV%',_:{},status:'unloaded',basePath:(function(){var d=window.CKEDITOR_BASEPATH||'';if(!d){var e=document.getElementsByTagName('script');for(var f=0;f<e.length;f++){var g=e[f].src.match(/(^|.*[\\\/])ckeditor(?:_basic)?(?:_source)?.js(?:\?.*)?$/i);if(g){d=g[1];break;}}}if(d.indexOf('://')==-1)if(d.indexOf('/')===0)d=location.href.match(/^.*?:\/\/[^\/]*/)[0]+d;else d=location.href.match(/^[^\?]*\/(?:)/)[0]+d;return d;})(),getUrl:function(d){if(d.indexOf('://')==-1&&d.indexOf('/')!==0)d=this.basePath+d;if(this.timestamp&&d.charAt(d.length-1)!='/')d+=(d.indexOf('?')>=0?'&':'?')+('t=')+this.timestamp;return d;}},b=window.CKEDITOR_GETURL;if(b){var c=a.getUrl;a.getUrl=function(d){return b.call(a,d)||c.call(a,d);};}return a;})();
+if(!window.CKEDITOR)window.CKEDITOR=(function(){var a={timestamp:'',version:'%VERSION%',revision:'%REV%',_:{},status:'unloaded',basePath:(function(){var d=window.CKEDITOR_BASEPATH||'';if(!d){var e=document.getElementsByTagName('script');for(var f=0;f<e.length;f++){var g=e[f].src.match(/(^|.*[\\\/])ckeditor(?:_basic)?(?:_source)?.js(?:\?.*)?$/i);if(g){d=g[1];break;}}}if(d.indexOf(':/')==-1)if(d.indexOf('/')===0)d=location.href.match(/^.*?:\/\/[^\/]*/)[0]+d;else d=location.href.match(/^[^\?]*\/(?:)/)[0]+d;return d;})(),getUrl:function(d){if(d.indexOf(':/')==-1&&d.indexOf('/')!==0)d=this.basePath+d;if(this.timestamp&&d.charAt(d.length-1)!='/')d+=(d.indexOf('?')>=0?'&':'?')+('t=')+this.timestamp;return d;}},b=window.CKEDITOR_GETURL;if(b){var c=a.getUrl;a.getUrl=function(d){return b.call(a,d)||c.call(a,d);};}return a;})();
 /*jsl:end*/
 
