http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/Project.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/Project.as 
b/Radii8Library/src/com/flexcapacitor/model/Project.as
new file mode 100644
index 0000000..29c87a1
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/Project.as
@@ -0,0 +1,1035 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       import com.flexcapacitor.controller.Radiate;
+       import com.flexcapacitor.services.IServiceEvent;
+       import com.flexcapacitor.services.IWPServiceEvent;
+       
+       import flash.events.Event;
+       import flash.events.IEventDispatcher;
+       import flash.net.URLVariables;
+       
+       import mx.utils.UIDUtil;
+       
+       /**
+        * Dispatched when project is saved
+        * */
+       [Event(name="saveResults", type="flash.events.Event")]
+       
+       /**
+        * Dispatched when project is opened
+        * */
+       [Event(name="projectOpened", type="flash.events.Event")]
+       
+       /**
+        * Project model
+        * */
+       public class Project extends ProjectData implements IProject, ISavable {
+               
+               /**
+                * Constructor
+                * */
+               public function Project() {
+                       nodeName = "project";
+                       nameIndex++;
+                       uid = UIDUtil.createUID();
+               }
+               
+               public static var PROJECT_OPENED:String = "projectOpened";
+               
+               /**
+                * Used when creating incremental project names
+                * */
+               public static var nameIndex:int;
+               
+               /**
+                * Used when creating incremental document names
+                * */
+               public var documentNameIndex:int;
+               
+               /**
+                * Default name for new documents
+                * */
+               public var defaultDocumentName:String = "Document";
+               
+               /**
+                * Set to true when saving because we need to wait until we get 
IDs for the documents
+                * */
+               private var deferSave:Boolean;
+               
+               /**
+                * Set to true when saving because we need to wait until we get 
IDs for the documents
+                * */
+               private var deferSaveLocations:String;
+               
+               
+               private var _documentsMetaData:Array = [];
+
+               /**
+                * Array of documents meta data
+                * */
+               public function get documentsMetaData():Array {
+                       return _documentsMetaData;
+               }
+
+               public function set documentsMetaData(value:Array):void {
+                       _documentsMetaData = value;
+               }
+
+
+               private var _projectData:IProjectData;
+
+               /**
+                * Defines the last restored saved project data object
+                * */
+               public function get projectData():IProjectData {
+                       return _projectData;
+               }
+
+               /**
+                * @private
+                */
+               public function set projectData(value:IProjectData):void {
+                       _projectData = value;
+               }
+
+               /**
+                * Create unique document name
+                * */
+               public function createDocumentName(document:IDocument = 
null):String {
+                       var name:String;
+                       
+                       if (document) {
+                               name = document.name ? document.name : 
defaultDocumentName;
+                       }
+                       
+                       var length:int = documents.length;
+                       
+                       for (var i:int;i<length;i++) {
+                               if (IDocument(documents[i])!=document) {
+                                       if (name==IDocument(documents[i]).name) 
{
+                                               name = name + " " + 
++documentNameIndex; // update name
+                                               i = 0; // start over checking 
again 
+                                       }
+                               }
+                       }
+                       
+                       return name;
+                       
+               }
+               
+               /**
+                * Adds a document if it hasn't been added yet
+                * */
+               public function addDocument(document:IDocument, 
overwrite:Boolean = false):void {
+                       var exists:Boolean = getDocumentExists(document);
+                       
+                       if (!exists || overwrite) {
+                               
+                               if (exists && overwrite) {
+                                       var documentToRemove:IDocumentData = 
getDocumentByUID(document.uid);
+                                       removeDocument(documentToRemove);
+                               }
+                               
+                               documents.push(document);
+                               document.name = createDocumentName(document);
+                               document.project = this;
+                               document.projectID = uid;
+                               isChanged = true;
+                       }
+                       else {
+                               Radiate.log.info("Document already added");
+                       }
+               }
+               
+               /**
+                * Remove a document 
+                * */
+               public function removeDocument(document:IDocumentData):void {
+                       var documentIndex:int = 
getDocumentIndexByUID(document.uid);
+                       
+                       if (documentIndex!=-1) {
+                               var removedArray:Array = 
documents.splice(documentIndex, 1);
+                               
+                               if (removedArray.length!=0 && 
removedArray[0]==document) {
+                                       //Radiate.log.info("Document removed " 
+ document.name);
+                               }
+                               isChanged = true;
+                       }
+                       else {
+                               //Radiate.log.info("Document not removed " + 
document.name);
+                       }
+               }
+               
+               /**
+                * Imports documents 
+                * */
+               public function 
importDocumentInstances(documentsToImport:Array, overwrite:Boolean = 
false):void {
+                       var metaDataLength:int = documentsMetaData.length;
+                       var iDocument:IDocument;
+                       var currentDocumentData:IDocumentData;
+                       var iDocumentMetaData:IDocumentMetaData;
+                       var documentsDataArrayLength:int;
+
+
+                       // loop through project's documents metadata
+                       for (var i:int;i<metaDataLength;i++) {
+                               iDocumentMetaData = 
IDocumentMetaData(documentsMetaData[i]);
+                               documentsDataArrayLength = 
documentsToImport.length;
+                               j = 0;
+                               
+                               // loop through all documents for match with 
project that owns document
+                               for (var j:int;j<documentsDataArrayLength;j++) {
+                                       iDocument = 
IDocument(documentsToImport[j]);
+                                       
+                                       
+                                       if (iDocument.uid == 
iDocumentMetaData.uid) {
+                                               //iDocument = 
currentDocumentData;
+                                               // should be created already
+                                               /*if (!(currentDocumentData is 
IDocument)) {
+                                                       iDocument = 
currentDocumentData.createInstance(currentDocumentData);
+                                               }*/
+                                               
+                                               
//Radiate.instance.addDocument(iDocument, this);
+                                               
//Radiate.instance.openDocument(iDocument);
+                                               
+                                               
addDocument(iDocument);//changed to document from documentdata
+                                               //log.info("  document added: " 
+ iDocumentData.name);
+                                       }
+                                       else {
+                                               //log.info("  document not 
added. " + iDocumentData.name);
+                                       }
+                               }
+                       }
+               }
+               
+               /**
+                * Opens a document if it isn't already open
+                * */
+               public function openDocument(document:IDocument, 
overwrite:Boolean = false):void {
+                       //document.open();
+                       //Radiate.instance.openDocument(document);
+               }
+               
+               /**
+                * Returns true if the document data is contained in the 
documents array
+                * */
+               public function 
getDocumentExists(data:IDocumentMetaData):Boolean {
+                       var length:int = documents.length;
+                       
+                       for (var i:int;i<length;i++) {
+                               if (IDocumentData(documents[i]).uid == 
data.uid) {
+                                       return true;
+                               }
+                       }
+                       
+                       return false;
+               }
+               
+               /**
+                * Returns true if the document exists in the documents array
+                * */
+               public function getDocumentExistsByID(uid:String):Boolean {
+                       var length:int = documents.length;
+                       
+                       for (var i:int;i<length;i++) {
+                               if (IDocumentData(documents[i]).uid == uid) {
+                                       return true;
+                               }
+                       }
+                       
+                       return false;
+               }
+               
+               /**
+                * Returns the document if it exists or null if not
+                * */
+               public function getDocumentByUID(uid:String):IDocumentData {
+                       var length:int = documents.length;
+                       
+                       for (var i:int;i<length;i++) {
+                               if (IDocumentData(documents[i]).uid == uid) {
+                                       return IDocumentData(documents[i]);
+                               }
+                       }
+                       
+                       return null;
+               }
+               
+               
+               /**
+                * Returns the document index
+                * */
+               public function getDocumentIndexByUID(uid:String):int {
+                       var length:int = documents.length;
+                       
+                       for (var i:int;i<length;i++) {
+                               if (IDocumentData(documents[i]).uid == uid) {
+                                       return i;
+                               }
+                       }
+                       
+                       return -1;
+               }
+               
+               /**
+                * @inheritDoc
+                * */
+               override public function toXML(representation:Boolean = 
false):XML {
+                       return marshall(XML_TYPE, representation) as XML;
+               }
+               
+               /**
+                * @inheritDoc
+                * */
+               override public function toString():String {
+                       
+                       return marshall(STRING_TYPE, true) as String;
+                       
+                       /*var documentData:IDocumentData;
+                       var documentXML:String;
+                       var xml:XML = new XML(<project/>);
+                       
+                       xml.@host = host;
+                       xml.@id = id;
+                       xml.@name = name;
+                       xml.@URI = URI;
+                       xml.@uid = uid;
+                       xml.documents = new XML(<documents/>);
+                       xml.@dateSaved = getTimeInHistory();
+                       
+                       if (!representation) {
+                               for (var i:int;i<documents.length;i++) {
+                                       documentData = documents[i];
+                                       documentXML = 
documentData.toMXMLString(true);
+                                       XML(xml.documents).appendChild( new 
XML(documentXML) );
+                               }
+                       }
+                       else {
+                               throw new Error("Representative XML is not 
implemented");
+                       }
+                       
+                       return xml.toXMLString();*/
+               }
+               
+               
+               /**
+                * Get source code for document. 
+                * Don't really like the way I'm doing this.
+                * I think it would be better to keep exporting and importing 
to external classes
+                * */
+               /*override public function getSource(target:Object = 
null):String {
+                       var documentData:IDocumentData;
+                       var documentXML:String;
+                       var xml:XML = new XML(<project/>);
+                       
+                       xml.@host = host;
+                       xml.@id = id;
+                       xml.@name = name;
+                       xml.@uri = uri;
+                       xml.@uid = uid;
+                       xml.@dateSaved = getTimeInHistory();
+                       
+                       //if (!representation) {
+                               xml.documents = new XML(<documents/>);
+                               
+                               for (var i:int;i<documents.length;i++) {
+                                       documentData = documents[i];
+                                       documentXML = 
documentData.marshall(METADATA_TYPE, true);
+                                       XML(xml.documents).appendChild( new 
XML(documentXML) );
+                               }
+                               
+                               for (var m:int;m<documents.length;m++) {
+                                       documentData = 
IDocumentData(documents[m]);
+                                       documentXML = 
XML(documentData.marshall(XML_TYPE, true));
+                                       XML(xml.documents).appendChild( 
documentXML );
+                               }
+                       //}
+                       
+                       return xml.toXMLString();
+                       
+               }*/
+               
+               
+               /**
+                * Serialize project data for saving. Export.
+                * */
+               override public function marshall(format:String = PROJECT_TYPE, 
representation:Boolean = false):Object {
+                       var documentsCount:int = documents.length;
+                       var documentsArray:Array = [];
+                       var documentData:IDocumentData;
+                       var projectData:ProjectData;
+                       var object:Object;
+                       
+                       // if string type get xml object. we will translate 
later
+                       if (format==STRING_TYPE || format==XML_TYPE ) {
+                               object = super.marshall(XML_TYPE, 
representation);
+                       }
+                       
+                       if (format==PROJECT_TYPE || format==METADATA_TYPE) {
+                               // get default document data information
+                               object = super.marshall(DOCUMENT_TYPE, 
representation);
+                               projectData = new ProjectData();
+                               projectData.unmarshall(object);
+                               
+                               for (var i:int;i<documentsCount;i++) {
+                                       documentData = 
IDocumentData(documents[i]);
+                                       
documentsArray.push(documentData.marshall(METADATA_TYPE, true));
+                               }
+                               
+                               // we're saving meta data but for readability 
we call it documents
+                               projectData.documents = documentsArray;
+                       
+                               return projectData;
+                       }
+                       else if (format==STRING_TYPE || format==XML_TYPE ) {
+                               var documentXML:XML;
+                               var xml:XML = XML(object);
+                               
+                               xml.documents = new XML(<documents/>);
+                               
+                               //if (!representation) {
+                                       for (var m:int;m<documents.length;m++) {
+                                               documentData = 
IDocumentData(documents[m]);
+                                               documentXML = 
XML(documentData.marshall(XML_TYPE, true));
+                                               XML(xml.documents).appendChild( 
documentXML );
+                                       }
+                               //}
+                               
+                               if (format==STRING_TYPE) {
+                                       return xml.toXMLString();
+                               }
+                               
+                               if (format==XML_TYPE) {
+                                       return xml;
+                               }
+                       }
+                       
+                       
+                       return object;
+               }
+               
+               /**
+                * Deserialize project data. 
+                * */
+               override public function unmarshall(data:Object):void {
+                       super.unmarshall(data);
+                       
+                       
+                       if (data is IDocumentMetaData || data is IDocumentData) 
{
+                               
+                               if (data is IDocumentData) {
+                                       source = data.source;
+                               }
+                               
+                               if (data is IProjectData) {
+                                       documentsMetaData = 
IProjectData(data).documents;
+                               }
+                       }
+                       else if (data is XML) {
+                               var documentsMetaDataList:XMLList = 
data.documents.document;
+                               
+                               source = XML(data).toXMLString();
+                               originalSource = XML(data).toXMLString();
+                               
+                               if (data && documentsMetaDataList.length()>0) {
+                                       var documentsCount:int = 
documentsMetaDataList.length();
+                                       var documentMetaData:DocumentMetaData;
+                                       var documentXML:XML;
+                                       var dateCreated:int;
+                                       
+                                       
+                                       for (var i:int;i<documentsCount;i++) {
+                                               documentXML = 
XML(documentsMetaDataList[i]);
+                                               documentMetaData = new 
DocumentMetaData();
+                                               
documentMetaData.unmarshall(documentXML);
+                                               
documentsMetaData.push(documentMetaData);
+                                       }
+                               }
+                       }
+                       /*
+                       var iProjectData:IProjectData = data as IProjectData;
+                       
+                       if (iProjectData) {
+                               projectData = iProjectData;
+                               documentsMetaData = iProjectData.documents;
+                       }*/
+               }
+               
+               /**
+                * Deserialize XML project data. 
+                * NOTE: TODO. We need to keep these in sync with the object 
representation. 
+                * */
+               /*public function unmarshallXML(data:XML):void {
+                       super.unmarshallXML(data);
+                       
+                       var documentsList:XMLList = data.documents.document;
+                       var documentXML:XML;
+                       var documentData:DocumentData;
+                       var dateCreated:int;
+                       
+                       if (data && documentsList.length()>0) {
+                               
+                               var length:int = documentsList.length();
+                               for (var i:int;i<length;i++) {
+                                       
+                                       documentXML = XML(documentsList[i]);
+                                       documentData = new DocumentData();
+                                       documentData.unmarshallXML(documentXML);
+                                       documentsMetaData.push(documentData);
+                                       //dateSaved = documentData.dateSaved;
+                                       
//Radiate.instance.createDocumentFromData(documentData);
+                                       
//Radiate.instance.addDocument(documentData.document);
+                               }
+                       }
+               }*/
+               
+               /**
+                * @inheritDoc
+                * */
+               override public function close():void {
+                       super.close();
+                       isOpen = false;
+               }
+               
+               /**
+                * @inheritDoc
+                * */
+               override public function open(location:String = 
REMOTE_LOCATION):void {
+                       var count:int = documents.length; //fromMetaData ? 
documentsMetaData.length : documents.length;
+                       var documentsArray:Array = documents; //fromMetaData ? 
documentsMetaData : documents;
+                       var documentMetaData:IDocumentMetaData;
+                       var documentData:IDocumentData;
+                       var iDocument:IDocument;
+                       var documentCreated:Boolean;
+                       var isRemote:Boolean = 
Radiate.getInstance().getIsRemoteLocation(location);
+                       var isLocal:Boolean = 
Radiate.getInstance().getIsLocalLocation(location);
+                       var isInternal:Boolean = 
Radiate.getInstance().getIsInternalLocation(location);
+                       
+                       // do documents have remote ID? if so we have to open 
from the server
+                       var needToWaitForDocumentsOpenResults:Boolean;
+                       
+                       // should set isOpen to true
+                       isOpen = true;
+                       
+                       //Radiate.instance.openPreviouslyOpenDocuments();
+                       
+                       
+                       // open documents
+                       //if (!fromMetaData) {
+                               
+                               for (var i:int;i<count;i++) {
+                                       iDocument = 
IDocument(documentsArray[i]);
+                                       
+                                       
+                                       if (isRemote) {
+                                               //documentCreated = 
getDocumentExists(iDocument);
+                                               
+                                               //if (!documentCreated) {
+                                               
+                                               if (iDocument && 
!iDocument.isOpen && iDocument.id!=null) {
+                                                       
+                                                       if (iDocument) {
+                                                               
DocumentData(iDocument).addEventListener(LoadResultsEvent.LOAD_RESULTS, 
documentRetrievedResultsHandler, false, 0, true);
+                                                       }
+                                                       
+                                                       
//Radiate.log.info("calling retrieve on document " + iDocument.name);
+                                                       iDocument.retrieve();
+                                               }
+                                               
+                                               //}
+                                               //else {
+                                                       //iDocument = 
getDocumentByID(documentMetaData.uid);
+                                                       //iDocument.open();
+                                                       
//Radiate.instance.openDocumentByData(iDocument, true);
+                                               //}
+                                       }
+                                       else if (isLocal) {
+                                               
iDocument.open(DocumentData.LOCAL_LOCATION);
+                                               
Radiate.instance.openDocumentByData(iDocument, true);
+                                       }
+                                       else if (isInternal) {
+                                               iDocument.open();
+                                               
Radiate.instance.openDocument(iDocument, location, true);
+                                       }
+                               }
+                       /*      
+                       }
+                       else {
+                               
+                               for (var j:int;j<length;j++) {
+                                       documentMetaData = 
IDocumentMetaData(documentsArray[j]);
+                                       
+                                       documentCreated = 
getDocumentExists(documentMetaData);
+                                       
+                                       if (!documentCreated) {
+                                               if (documentData is 
DocumentData) {
+                                                       
DocumentData(documentData).addEventListener(DocumentData.RETRIEVED_RESULTS, 
documentRetrievedResultsHandler, false, 0, true);
+                                               }
+                                               
+                                               Radiate.log.info("calling 
retrieve on document " + documentData.name);
+                                               documentData.retrieve();
+                                       }
+                                       else {
+                                               iDocument = 
getDocumentByID(documentMetaData.uid);
+                                               iDocument.open();
+                                               
Radiate.instance.openDocumentByData(iDocument, true);
+                                       }
+                               }
+                       }*/
+                       
+                       /*
+                       if (!needToWaitForDocumentsOpenResults) {
+                               //super.open(local);
+                       }
+                       else {
+                               // we need to open the project with the remote 
ID
+                               deferOpen = true;
+                       }*/
+               
+               }
+               
+               /**
+                * @inheritDoc
+                * */
+               public function openFromMetaData(location:String = 
REMOTE_LOCATION):void {
+                       var count:int = documentsMetaData.length;
+                       var documentsArray:Array = documentsMetaData;
+                       var documentMetaData:IDocumentMetaData;
+                       //var documentData:IDocumentData;
+                       var iDocument:IDocument;
+                       var iDocumentData:IDocumentData;
+                       var documentCreated:Boolean;
+                       var radiate:Radiate = Radiate.getInstance();
+                       
+                       // do documents have remote ID? if so we have to open 
from the server
+                       var needToWaitForDocumentsOpenResults:Boolean;
+                       
+                       // should set isOpen to true
+                       isOpen = true;
+                       
+                       //Radiate.instance.openPreviouslyOpenDocuments();
+                       
+                       for (var j:int;j<count;j++) {
+                               documentMetaData = 
IDocumentMetaData(documentsArray[j]);
+                               
+                               documentCreated = 
getDocumentExists(documentMetaData);
+                               
+                               if (!documentCreated) {
+                                       iDocument = 
radiate.createDocumentFromMetaData(documentMetaData);
+                                       
DocumentData(iDocument).addEventListener(LoadResultsEvent.LOAD_RESULTS, 
documentRetrievedResultsHandler, false, 0, true);
+                                       //Radiate.log.info("calling retrieve on 
document " + iDocument.name);
+                                       iDocument.retrieve();
+                                       documents.push(iDocument);
+                                       iDocument.project = this;
+                                       /*
+                                       if (documentData.id==null) {
+                                               
needToWaitForDocumentsOpenResults = true;
+                                       }*/
+                               }
+                               else {
+                                       iDocumentData = 
getDocumentByUID(documentMetaData.uid);
+                                       iDocumentData.open(location);
+                                       
Radiate.instance.openDocumentByData(iDocumentData, true);
+                               }
+                       }
+                       
+                       
+                       // project is already open...?
+                       /*if (!needToWaitForDocumentsOpenResults) {
+                               //super.open(local);
+                       }
+                       else {
+                               // we need to open the project with the remote 
ID
+                               deferOpen = true;
+                       }*/
+               
+               }
+               
+               /**
+                * @inheritDoc
+                * */
+               override public function retrieve(local:Boolean = false):void {
+                       var length:int = documentsMetaData.length;
+                       var documentData:IDocumentData;
+                       var documentsArray:Array = documents.length ? documents 
: documentsMetaData;
+                       
+                       // do documents have remote ID? if so we have to open 
from the server
+                       var needToWaitForDocumentsOpenResults:Boolean = false;
+                       
+                       // open documents
+                       for (var i:int;i<length;i++) {
+                               documentData = IDocumentData(documentsArray[i]);
+                               
+                               if (documentData is DocumentData) {
+                                       
DocumentData(documentData).addEventListener(LoadResultsEvent.LOAD_RESULTS, 
documentRetrievedResultsHandler, false, 0, true);
+                               }
+                               
+                               Radiate.log.info("calling open on document " + 
documentData.name);
+                               documentData.retrieve(local);
+                               
+                               if (documentData.id==null) {
+                                       needToWaitForDocumentsOpenResults = 
true;
+                               }
+                       }
+                       
+                       if (!needToWaitForDocumentsOpenResults) {
+                               //super.open(local);
+                       }
+                       else {
+                               // we need to open the project with the remote 
ID
+                               //deferOpen = true;
+                       }
+               
+               }
+               
+               /**
+                * @inheritDoc
+                * */
+               override public function save(locations:String = 
REMOTE_LOCATION, options:Object = null):Boolean {
+                       var length:int = documents.length;
+                       var documentData:IDocumentData;
+                       var saveRemote:Boolean = 
locations.indexOf(REMOTE_LOCATION)!=-1;
+                       var saveLocally:Boolean = 
locations.indexOf(LOCAL_LOCATION)!=-1;
+                       
+                       // do all documents have remote ID? if not we have to 
save again when 
+                       // we get an ID from the server
+                       var needToWaitForDocumentsSaveResults:Boolean = false;
+                       
+                       if (id==null) {
+                               firstTimeSave = true;
+                       }
+                       
+                       // save documents
+                       for (var i:int;i<length;i++) {
+                               documentData = IDocumentData(documents[i]);
+                               
+                               if (documentData.isChanged || 
documentData.id==null) {
+                                       if (saveRemote && documentData is 
DocumentData) {
+                                               
DocumentData(documentData).addEventListener(SaveResultsEvent.SAVE_RESULTS, 
documentSaveResultsHandler, false, 0, true);
+                                       }
+                                       
+                                       if (saveRemote && 
documentData.id==null) {
+                                               
needToWaitForDocumentsSaveResults = true;
+                                       }
+                                       
+                                       documentData.save(locations);
+                               }
+                       }
+                       
+                       if (!needToWaitForDocumentsSaveResults) {
+                               var savedLocally:Boolean = 
super.save(locations);
+                       }
+                       else {
+                               // we need to save the project when we receive 
the response with the remote ID
+                               deferSave = true;
+                               deferSaveLocations = locations;
+                       }
+               
+                       return savedLocally;
+               }
+               
+               
+               /**
+                * Creates an object to send to the server
+                * */
+               override public function toSaveFormObject():URLVariables {
+                       var object:URLVariables = super.toSaveFormObject();
+                       var content:String;
+                       
+                       object.categories = PROJECT_CATEGORY;
+                       content = String(marshall(STRING_TYPE, false));
+                       object.content = content;
+                       object["custom[source]"] = content;
+                       source = content;
+                       
+                       return object;
+               }
+               
+               /**
+                * Result from project save fault
+                * */
+               override public function 
saveFaultHandler(event:IServiceEvent):void {
+                       super.saveFaultHandler(event);
+                       
+                       //trace("Save Project Fault");
+                       Radiate.log.info("Error when trying to save "+ name + 
".");
+                       deferSave = false;
+                       dispatchEvent(event as Event);
+               }
+               
+               /**
+                * Result from project save results 
+                * */
+               override public function 
saveResultsHandler(event:IWPServiceEvent):void {
+                       super.saveResultsHandler(event);
+                       
+                       checkProjectHasChanged();
+                       
+                       if (firstTimeSave) {
+                               firstTimeSave = false;
+                               super.save(REMOTE_LOCATION);
+                       }
+                       else {
+                               deferSave = false;
+                               dispatchEvent(event as Event);
+                               //Radiate.instance.setLastSaveDate();
+                       }
+                       //Radiate.log.info("PROJECT - Success saving project "+ 
name + ".");
+               }
+               
+               /**
+                * Result from open result
+                * */
+               override public function 
openResultsHandler(event:IServiceEvent):void {
+                       super.openResultsHandler(event);
+                       
+                       // add assets
+                       if (documents.length==0) {
+                               dispatchProjectOpened();
+                       }
+               }
+               
+               /**
+                * Project opened
+                * */
+               public function dispatchProjectOpened():void {
+                       //Radiate.log.info("Project open complete");
+                       isOpen = true;
+                       dispatchEvent(new Event(PROJECT_OPENED));
+               }
+               
+               /**
+                * Result from retrieved results
+                * */
+               public function 
documentRetrievedResultsHandler(event:LoadResultsEvent):void {
+                       var currentDocumentData:IDocumentData = 
IDocumentData(event.currentTarget);
+                       var documentsArray:Array = documents; 
//documentsMetaData;//documents.length ? documents : documentsMetaData;
+                       var length:int = documentsArray.length;
+                       var documentData:IDocumentData;
+                       var iDocument:IDocument;
+                       var resultsNotIn:Array = [];
+                       var openNotSuccessful:Array = [];
+                       var data:Object = event.data;
+                       
+                       //Radiate.log.info("Is document " + 
event.currentTarget.name + " open: "+ event.successful);
+                       
+                       
DocumentData(currentDocumentData).removeEventListener(LoadResultsEvent.LOAD_RESULTS,
 documentRetrievedResultsHandler);
+                       
+                       // check if all documents have loaded
+                       for (var i:int;i<length;i++) {
+                               documentData = IDocumentData(documentsArray[i]);
+                               
+                               if (documentData is DocumentData) {
+                                       
+                                       // check if open is in progress
+                                       if 
(DocumentData(documentData).openInProgress) {
+                                               resultsNotIn.push(documentData);
+                                       }
+                                       
+                                       // check if open is unsuccessful
+                                       if (!documentData.openSuccessful) {
+                                               
openNotSuccessful.push(documentData.name);
+                                       }
+                               }
+                       }
+                       
+                       if (!currentDocumentData.openSuccessful) {
+                               Radiate.log.info("The document '" + 
currentDocumentData.name + "' could not be loaded because of the following 
error: " + event.message);
+                               
+                               if (event.faultEvent) {
+                                       Radiate.log.info(event.faultEvent + "");
+                               }
+                       }
+                       
+                       // ALSO NEED TO UPDATE CODE IN OPEN RESULTS HANDLER
+                       // all documents opened
+                       if (resultsNotIn.length==0) {
+                               
+                               if (openNotSuccessful.length>0) {
+                                       //Radiate.log.info("These documents 
could not be opened: " + openNotSuccessful);
+                                       //Radiate.log.info("Document error 
occurred for "+documentData.name+": " + event.message);
+                               }
+                               
+                               dispatchProjectOpened();
+                       }
+                       
+                       // open document now that it's loaded
+                       // move this to Radiate in project open event (its a 
new event)
+                       if (currentDocumentData.openSuccessful) {
+                               if (!(currentDocumentData is IDocument)) {
+                                       iDocument = 
currentDocumentData.createInstance(currentDocumentData);
+                               }
+                               else {
+                                       iDocument = 
IDocument(currentDocumentData);
+                               }
+                               
+                               // we are over writing the previous instance - 
+                               // but should we unmarshall it? 
+                               Radiate.instance.addDocument(iDocument, this, 
true);
+                               Radiate.instance.openDocument(iDocument);
+                       }
+                       
+                       /*if (deferOpen) {
+                               super.open();
+                               deferOpen = false;
+                       } else {
+                               
+                       }*/
+               }
+               
+               /**
+                * Result from save results
+                * */
+               public function 
documentSaveResultsHandler(event:SaveResultsEvent):void {
+                       //trace("Document save results");
+                       //Radiate.log.info("Is document " + 
event.currentTarget.name + " saved: "+ event.successful);
+                       var length:int = documents.length;
+                       var document:IDocumentData;
+                       var resultsNotIn:Array = [];
+                       var unsuccessfulSaves:Array = [];
+                       var currentDocument:IDocumentData;
+                       
+                       currentDocument = DocumentData(event.currentTarget);
+                       
+                       if (currentDocument is IEventDispatcher) {
+                               
IEventDispatcher(currentDocument).removeEventListener(SaveResultsEvent.SAVE_RESULTS,
 documentSaveResultsHandler);
+                       }
+                       
+                       for (var i:int;i<length;i++) {
+                               document = IDocumentData(documents[i]);
+                               
+                               if (document is DocumentData) {
+                                       
+                                       // check if saving is in progress
+                                       if 
(DocumentData(document).saveInProgress) {
+                                               resultsNotIn.push(document);
+                                       }
+                                       
+                                       // check if save is unsuccessful
+                                       if (!document.saveSuccessful) {
+                                               
unsuccessfulSaves.push(document.name);
+                                       }
+                               }
+                       }
+                       
+                       if (!currentDocument.saveSuccessful) {
+                               
+                               if (!Radiate.getInstance().isUserLoggedIn) {
+                                       Radiate.log.info("The document, '" + 
currentDocument.name + "' was not saved because the user is not logged in.");
+                               }
+                               else {
+                                       Radiate.log.info("The document, '" + 
currentDocument.name + "' was not saved because of the following error: " + 
event.message);
+                               }
+                               
+                               if (event.faultEvent) {
+                                       Radiate.log.info(event.faultEvent + "");
+                               }
+                       }
+                       
+                       if (resultsNotIn.length==0) {
+                               //Radiate.log.info(name + " save complete");
+                               
+                               // if document was not saved recently 
saveSuccessful may be false?
+                               if (unsuccessfulSaves.length>0) {
+                                       //Radiate.log.info("These documents 
could not be saved: " + unsuccessfulSaves);
+                               }
+                               else {
+                                       //isChanged = false; // hardcoding for 
now until checkProjectHasChanged is fixed
+                               }
+                       }
+                       
+                       if (deferSave) {
+                               super.save(deferSaveLocations);
+                               deferSave = false;
+                       } else {
+                               
+                       }
+                       
+                       
+                       
//DocumentData(document).addEventListener(DocumentData.SAVE_RESULTS, 
documentSaveResultsHandler, false, 0, true);
+                       
+               }
+               
+               /**
+                * Check if project source has changed
+                * */
+               public function checkProjectHasChanged():Boolean {
+                       //var content:String = String(marshall(STRING_TYPE, 
false));
+                       var contentXML:XML = XML(marshall(XML_TYPE, false));
+                       var sourceXML:XML = new XML(source);
+                       var pattern:RegExp = / dateSaved=\"\d+\"/g;
+                       
+                       //delete contentXML.@dateSaved;
+                       
+                       var contentXMLValue:String = 
contentXML.toXMLString().replace(pattern, "");
+                       var sourceXMLValue:String = 
sourceXML.toXMLString().replace(pattern, "");
+                       
+                       if (contentXMLValue!=sourceXMLValue) { // will always 
be false because date and time is saved on each call
+                               isChanged = true;
+                       }
+                       else {
+                               isChanged = false;
+                       }
+                       //isChanged = false; // setting to false for now until 
we find a better way
+                       
+                       return isChanged;
+               }
+               
+               
+               /**
+                * Get a list of documents for local storage. If open is set to 
true then only returns open documents.
+                * */
+               public function getSavableDocumentsData(open:Boolean = false, 
metaData:Boolean = false):Array {
+                       var documentsArray:Array = [];
+                       var length:int = documents.length;
+                       var iDocument:IDocument;
+                       
+                       
+                       for (var i:int;i<length;i++) {
+                               iDocument = IDocument(documents[i]);
+                               //Radiate.log.info("Exporting document " + 
iDocument.name);
+                               
+                               if (open) {
+                                       if (iDocument.isOpen) {
+                                               if (metaData) {
+                                                       
documentsArray.push(iDocument.toMetaData());
+                                               }
+                                               else {
+                                                       
documentsArray.push(iDocument.marshall());
+                                                       
//Radiate.log.info("Exporting document " + iDocument.source);
+                                               }
+                                       }
+                               }
+                               else {
+                                       if (metaData) {
+                                               
documentsArray.push(iDocument.toMetaData());
+                                       }
+                                       else {
+                                               
documentsArray.push(iDocument.marshall(DOCUMENT_TYPE, false));
+                                       }
+                               }
+                       }
+                       
+                       
+                       return documentsArray;
+               }
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/ProjectData.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/ProjectData.as 
b/Radii8Library/src/com/flexcapacitor/model/ProjectData.as
new file mode 100644
index 0000000..5426728
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/ProjectData.as
@@ -0,0 +1,63 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       
+       
+       /**
+        * Holds project data for storage
+        * */
+       [RemoteClass(alias="ProjectData")]
+       public class ProjectData extends DocumentData implements IProjectData {
+               
+               
+               public function ProjectData() {
+                       
+               }
+
+
+               private var _documentsData:Array = [];
+
+               /**
+                * @inheritDoc
+                * */
+               public function get documentsData():Array {
+                       return _documentsData;
+               }
+
+               public function set documentsData(value:Array):void {
+                       _documentsData = value;
+               }
+
+
+               private var _documents:Array = [];
+
+               /**
+                * @inheritDoc
+                * */
+               public function get documents():Array {
+                       return _documents;
+               }
+
+               public function set documents(value:Array):void {
+                       _documents = value;
+               }
+               
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/ProjectDataDescriptor.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/ProjectDataDescriptor.as 
b/Radii8Library/src/com/flexcapacitor/model/ProjectDataDescriptor.as
new file mode 100644
index 0000000..9079352
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/ProjectDataDescriptor.as
@@ -0,0 +1,107 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       import mx.collections.ICollectionView;
+       import mx.controls.treeClasses.DefaultDataDescriptor;
+       
+       /**
+        * Describes how project data is displayed in a tree
+        * */
+       public class ProjectDataDescriptor extends DefaultDataDescriptor {
+               
+               
+               public function ProjectDataDescriptor() {
+                       super();
+               }
+               
+               /**
+                * Get documents for now
+                * */
+               override public function getChildren(node:Object, model:Object 
= null):ICollectionView {
+                       if ("documents" in node) {
+                               return node.documents;
+                       }
+                       
+                       return null;
+               }
+               
+       
+           /**
+            *  Tests a node for termination.
+            *  Branches are non-terminating but are not required to have any 
leaf nodes.
+            *  If the node is XML, returns <code>true</code> if the node has 
children
+            *  or a <code>true isBranch</code> attribute.
+            *  If the node is an object, returns <code>true</code> if the node 
has a
+            *  (possibly empty) <code>children</code> field.
+            *
+            *  @param node The node object currently being evaluated.
+            *  @param model The collection that contains the node; ignored by 
this class.
+            *  
+            *  @return <code>true</code> if this node is non-terminating.
+            *  
+            *  @langversion 3.0
+            *  @playerversion Flash 9
+            *  @playerversion AIR 1.1
+            *  @productversion Flex 3
+            */
+           override public function isBranch(node:Object, model:Object = 
null):Boolean
+           {
+               if (node == null)
+                   return false;
+                   
+               var branch:Boolean = false;
+                   
+               if (node is XML)
+               {
+                   var childList:XMLList = node.children();
+                   //accessing non-required e4x attributes is quirky
+                   //but we know we'll at least get an XMLList
+                   var branchFlag:XMLList = node.@isBranch;
+                   //check to see if a flag has been set
+                   if (branchFlag.length() == 1)
+                   {
+                       //check flag and return (this flag overrides 
termination status)
+                       if (branchFlag[0] == "true")
+                           branch = true;
+                   }
+                   //since no flags, we'll check to see if there are children
+                   else if (childList.length() != 0)
+                   {
+                       branch = true;
+                   }
+               }
+               else if (node is Object)
+               {
+                   try
+                   {
+                       if (node.documents != undefined)
+                       {
+                           branch = true;
+                       }
+                   }
+                   catch(e:Error)
+                   {
+                   }
+               }
+               return branch;
+           }
+
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/ProjectMetaData.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/ProjectMetaData.as 
b/Radii8Library/src/com/flexcapacitor/model/ProjectMetaData.as
new file mode 100644
index 0000000..5627c9c
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/ProjectMetaData.as
@@ -0,0 +1,33 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       
+       /**
+        * Used to store basic information about a project for later retrieval.
+        * */
+       [RemoteClass(alias="ProjectMetaData")]
+       public class ProjectMetaData extends DocumentMetaData implements 
IProjectMetaData {
+               
+               public function ProjectMetaData() {
+                       
+               }
+               
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/SaveResultsEvent.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/SaveResultsEvent.as 
b/Radii8Library/src/com/flexcapacitor/model/SaveResultsEvent.as
new file mode 100644
index 0000000..00d9115
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/SaveResultsEvent.as
@@ -0,0 +1,81 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       import com.flexcapacitor.services.IWPServiceEvent;
+       import com.flexcapacitor.services.ServiceEvent;
+       
+       import flash.events.Event;
+       
+       /**
+        * Indicates if save of document was successful
+        * */
+       public class SaveResultsEvent extends ServiceEvent implements 
IWPServiceEvent {
+               
+               /**
+                * Event dispatched when the save results are returned
+                * */
+               public static const SAVE_RESULTS:String = "saveResults";
+               
+
+               private var _call:String;
+
+               /**
+                * 
+                * */
+               public function get call():String {
+                       return _call;
+               }
+
+               public function set call(value:String):void {
+                       _call = value;
+               }
+
+               private var _text:String;
+
+               private var _message:String;
+
+               /**
+                * 
+                * */
+               public function get message():String {
+                       return _message;
+               }
+
+               public function set message(value:String):void {
+                       _message = value;
+               }
+
+               
+               public function SaveResultsEvent(type:String, 
bubbles:Boolean=false, cancelable:Boolean=false, successful:Boolean = false)
+               {
+                       super(type, bubbles, cancelable);
+                       this.successful = successful;
+               }
+               
+               /**
+                * Indicates if save was successful
+                * */
+               public var successful:Boolean;
+               
+               override public function clone():Event {
+                       return new SaveResultsEvent(type, bubbles, cancelable, 
successful);
+               }
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/SavedData.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/SavedData.as 
b/Radii8Library/src/com/flexcapacitor/model/SavedData.as
new file mode 100644
index 0000000..d2e7405
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/SavedData.as
@@ -0,0 +1,76 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       
+       
+       /**
+        * Class used to store projects, documents and resources
+        * */
+       [RemoteClass(alias="SavedData")]
+       public class SavedData implements ISavedData {
+               
+               public function SavedData() {
+                       modified = created = new Date().time;
+               }
+               
+               
+               private var _version:uint = 1;
+
+               public function get version():uint {
+                       return _version;
+               }
+
+               public function set version(value:uint):void {
+                       _version = value;
+               }
+               
+               public var saveCount:int;
+               
+               
+               public var created:uint;
+               public var modified:uint;
+               private var _modifiedValue:uint;
+
+               public function get modifiedValue():uint {
+                       return _modifiedValue;
+               }
+
+               public function set modifiedValue(value:uint):void {
+                       _modifiedValue = value;
+               }
+
+               
+               public var workspaces:Array = [];
+               
+               public var projects:Array = [];
+               
+               public var documents:Array = [];
+               
+               public var resources:Array = [];
+               
+               
+               
+               public function unmarshall(data:Object):void {
+                       
+                       
+                       
+               }
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/Settings.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/Settings.as 
b/Radii8Library/src/com/flexcapacitor/model/Settings.as
new file mode 100644
index 0000000..1d2b0cb
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/Settings.as
@@ -0,0 +1,82 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       
+       
+       /**
+        * Class used to store settings and projects
+        * */
+       [RemoteClass(alias="Settings")]
+       public class Settings implements ISettings {
+               
+               public function Settings() {
+                       
+                       lastOpened = modified = created = new Date().time;
+               }
+               
+               private var _version:uint = 1;
+
+               public function get version():uint {
+                       return _version;
+               }
+
+               public function set version(value:uint):void {
+                       _version = value;
+               }
+               
+               
+               public var created:uint;
+               public var modified:uint;
+               private var _modifiedValue:uint;
+
+               public function get modifiedValue():uint {
+                       return new Date().time;
+               }
+
+               public function set modifiedValue(value:uint):void {
+                       _modifiedValue = value;
+               }
+
+               public var lastOpened:uint; 
+               
+               public var configuration:Object;
+               
+               public var openProjects:Array = [];
+               
+               public var openDocuments:Array = [];
+               
+               public var openWorkspace:Array = [];
+               
+               public var selectedDocument:IDocumentMetaData;
+               
+               public var selectedProject:IDocumentMetaData;
+               
+               public var saveCount:int;
+               
+               
+               
+               public function unmarshall(data:Object):void {
+                       
+                       
+                       
+               }
+               
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/Size.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/Size.as 
b/Radii8Library/src/com/flexcapacitor/model/Size.as
new file mode 100644
index 0000000..e4edcc8
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/Size.as
@@ -0,0 +1,61 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       
+       /**
+        * Base class for document sizes
+        * */
+       public class Size {
+               
+               
+               public function Size(width:String="0", height:String="0", 
ppi:int=0)
+               {
+                       this.width = width;
+                       this.height = height;
+                       this.ppi = ppi;
+               }
+               
+               /**
+                * 
+                * */
+               public var name:String;
+               
+               /**
+                * Width can be percent
+                * */
+               public var width:String;
+               
+               /**
+                * Height can be percent
+                * */
+               public var height:String;
+               
+               /**
+                * Points per inch
+                * */
+               public var ppi:int;
+               
+               /**
+                * Screen type
+                * */
+               public var type:String;
+               
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/StyleMetaData.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/StyleMetaData.as 
b/Radii8Library/src/com/flexcapacitor/model/StyleMetaData.as
new file mode 100644
index 0000000..530f9ea
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/StyleMetaData.as
@@ -0,0 +1,102 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+package com.flexcapacitor.model {
+       import mx.styles.IStyleClient;
+       
+       /**
+        * Contains information on style metadata
+        * */
+       public class StyleMetaData extends MetaData {
+               
+               /**
+                * Constructor
+                * */
+               public function StyleMetaData(item:XML = null, target:* = null) 
{
+                       if (item) unmarshall(item, target);
+               }
+               
+               /**
+                * 
+                * */
+               public var inherit:Boolean;
+               
+               /**
+                * Set to true if style is defined on the target. 
+                * In other words the user set it in MXML or AS3 and it is not 
inherited.
+                * styleClient.getStyle(thisStyle)!==undefined. 
+                * */
+               public var definedInline:Boolean;
+               
+               /**
+                * 
+                * */
+               public var inheritedValue:*;
+               
+               /**
+                * 
+                * */
+               public var nonInheritedValue:*;
+               
+               /**
+                * Import metadata XML Style node into this instance
+                * */
+               override public function unmarshall(item:XML, target:* = null, 
getValue:Boolean = true):void {
+                       super.unmarshall(item, target, getValue);
+                       
+                       var args:XMLList = item.arg;
+                       var keyName:String;
+                       var keyValue:String;
+                       
+                       
+                       for each (var arg:XML in args) {
+                               keyName = arg.@key;
+                               
+                               if (keyName=="inherit") {
+                                       inherit = keyValue=="no";//bug?
+                                       break;
+                               }
+                               
+                       }
+                       
+                       // this shows if it's defined at all 
+                       definedInline = target && target is IStyleClient && 
target.getStyle(name)!==undefined;
+                       
+                       if (!definedInline) {
+                               inheritedValue = target.getStyle(name);
+                               nonInheritedValue = undefined;
+                               value = inheritedValue;
+                               textValue = "" + inheritedValue;
+                       }
+                       else {
+                               // don't know how to get this value -
+                               // UPDATE: there is CSS code in MiniInspector 
to check if a value is 
+                               // set inline or inherited
+                               // we also have the inheritedStyles and 
nonInherited object on IStyleClient
+                               inheritedValue = undefined;
+                               nonInheritedValue = target.getStyle(name);
+                               value = nonInheritedValue;
+                               textValue = "" + nonInheritedValue;
+                       }
+                       
+                       
+                       
+               }
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/model/VisualElementVO.as
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/model/VisualElementVO.as 
b/Radii8Library/src/com/flexcapacitor/model/VisualElementVO.as
new file mode 100644
index 0000000..07e2d3b
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/model/VisualElementVO.as
@@ -0,0 +1,64 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+//  Licensed to the Apache Software Foundation (ASF) under one or more
+//  contributor license agreements.  See the NOTICE file distributed with
+//  this work for additional information regarding copyright ownership.
+//  The ASF licenses this file to You under the Apache License, Version 2.0
+//  (the "License"); you may not use this file except in compliance with
+//  the License.  You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+//  Unless required by applicable law or agreed to in writing, software
+//  distributed under the License is distributed on an "AS IS" BASIS,
+//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+//  See the License for the specific language governing permissions and
+//  limitations under the License.
+//
+////////////////////////////////////////////////////////////////////////////////
+
+
+
+
+/**
+ * Used for display in the Outline view
+ * */
+package com.flexcapacitor.model {
+       
+       import com.flexcapacitor.utils.InspectorUtils;
+       
+       import flash.display.DisplayObjectContainer;
+       
+       import mx.collections.ArrayCollection;
+
+       public class VisualElementVO {
+
+               public var id:String;
+               public var name:String;
+               public var type:String;
+               public var superClass:String;
+               public var element:Object;
+               public var children:ArrayCollection;
+               public var parent:DisplayObjectContainer;
+               public var label:String;
+
+               public function VisualElementVO() {
+
+               }
+
+               public static function unmarshall(element:*):VisualElementVO {
+                       var vo:VisualElementVO = new VisualElementVO();
+                       
+                       vo.id =                 
InspectorUtils.getIdentifier(element);
+                       vo.name =               InspectorUtils.getName(element);
+                       vo.type =               
InspectorUtils.getClassName(element);
+                       vo.superClass = 
InspectorUtils.getSuperClassName(element);
+                       vo.element =    element;
+                       vo.label =              vo.type;
+                       
+                       // get vo.children manually
+
+                       return vo;
+               }
+       }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/skins/DeviceImage.mxml
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/skins/DeviceImage.mxml 
b/Radii8Library/src/com/flexcapacitor/skins/DeviceImage.mxml
new file mode 100644
index 0000000..c00cd81
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/skins/DeviceImage.mxml
@@ -0,0 +1,92 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+Licensed to the Apache Software Foundation (ASF) under one or more
+contributor license agreements.  See the NOTICE file distributed with
+this work for additional information regarding copyright ownership.
+The ASF licenses this file to You under the Apache License, Version 2.0
+(the "License"); you may not use this file except in compliance with
+the License.  You may obtain a copy of the License at
+
+http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+-->
+
+<!--- The default skin class for a Spark SkinnableContainer container.  
+
+     @see spark.components.SkinnableContainer
+        
+      @langversion 3.0
+      @playerversion Flash 10
+      @playerversion AIR 1.5
+      @productversion Flex 4
+-->
+<s:Skin xmlns:fx="http://ns.adobe.com/mxml/2009"; 
xmlns:s="library://ns.adobe.com/flex/spark" 
+    xmlns:fb="http://ns.adobe.com/flashbuilder/2009"; alpha.disabled="0.5">
+
+    <fx:Metadata>
+    <![CDATA[ 
+        /** 
+         * @copy spark.skins.spark.ApplicationSkin#hostComponent
+         */
+        [HostComponent("spark.components.SkinnableContainer")]
+    ]]>
+    </fx:Metadata> 
+    
+    <fx:Script fb:purpose="styling">
+        <![CDATA[         
+            /**
+             *  @private
+             */
+            override protected function 
updateDisplayList(unscaledWidth:Number, unscaledHeight:Number) : void
+            {
+                // Push backgroundColor and backgroundAlpha directly.
+                // Handle undefined backgroundColor by hiding the background 
object.
+                if (isNaN(getStyle("backgroundColor")))
+                {
+                    background.visible = false;
+                }
+                else
+                {
+                    background.visible = true;
+                    bgFill.color = getStyle("backgroundColor");
+                    bgFill.alpha = getStyle("backgroundAlpha");
+                }
+                
+                super.updateDisplayList(unscaledWidth, unscaledHeight);
+            }
+        ]]>        
+    </fx:Script>
+    
+    <s:states>
+        <s:State name="normal" />
+        <s:State name="disabled" />
+    </s:states>
+    
+    <!--- Defines the appearance of the SkinnableContainer class's background. 
-->
+    <s:Rect id="background" left="0" right="0" top="0" bottom="0">
+        <s:fill>
+            <!--- @private -->
+            <s:SolidColor id="bgFill" color="#FFFFFF"/>
+        </s:fill>
+    </s:Rect>
+    
+    <!--
+        Note: setting the minimum size to 0 here so that changes to the host 
component's
+        size will not be thwarted by this skin part's minimum size.   This is 
a compromise,
+        more about it here: http://bugs.adobe.com/jira/browse/SDK-21143
+    -->
+    <!--- @copy spark.components.SkinnableContainer#contentGroup -->
+    <s:Group id="contentGroup" left="0" right="0" top="0" bottom="0" 
minWidth="0" minHeight="0">
+        <s:layout>
+            <s:BasicLayout/>
+        </s:layout>
+    </s:Group>
+
+</s:Skin>

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/skins/DeviceSkin.mxml
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/skins/DeviceSkin.mxml 
b/Radii8Library/src/com/flexcapacitor/skins/DeviceSkin.mxml
new file mode 100644
index 0000000..6d65b42
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/skins/DeviceSkin.mxml
@@ -0,0 +1,108 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+Licensed to the Apache Software Foundation (ASF) under one or more
+contributor license agreements.  See the NOTICE file distributed with
+this work for additional information regarding copyright ownership.
+The ASF licenses this file to You under the Apache License, Version 2.0
+(the "License"); you may not use this file except in compliance with
+the License.  You may obtain a copy of the License at
+
+http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+-->
+
+
+<!--- The default skin class for a Spark SkinnableContainer container.  
+
+     @see spark.components.SkinnableContainer
+        
+      @langversion 3.0
+      @playerversion Flash 10
+      @playerversion AIR 1.5
+      @productversion Flex 4
+-->
+<s:Skin xmlns:fx="http://ns.adobe.com/mxml/2009"; 
xmlns:s="library://ns.adobe.com/flex/spark" 
+    xmlns:fb="http://ns.adobe.com/flashbuilder/2009"; alpha.disabled="0.5">
+
+    <fx:Metadata>
+    <![CDATA[ 
+        /** 
+         * @copy spark.skins.spark.ApplicationSkin#hostComponent
+         */
+        [HostComponent("spark.components.SkinnableContainer")]
+    ]]>
+    </fx:Metadata> 
+    
+    <fx:Script fb:purpose="styling">
+        <![CDATA[         
+            /**
+             *  @private
+             */
+            override protected function 
updateDisplayList(unscaledWidth:Number, unscaledHeight:Number) : void
+            {
+                               //trace("IN SKIN");
+                // Push backgroundColor and backgroundAlpha directly.
+                // Handle undefined backgroundColor by hiding the background 
object.
+                /*if (isNaN(getStyle("backgroundColor")))
+                {
+                    background.visible = false;
+                }
+                else
+                {
+                    background.visible = true;
+                    bgFill.color = getStyle("backgroundColor");
+                    bgFill.alpha = getStyle("backgroundAlpha");
+                }*/
+                
+                super.updateDisplayList(unscaledWidth, unscaledHeight);
+            }
+        ]]>        
+    </fx:Script>
+    
+    <s:states>
+        <s:State name="portrait" />
+        <s:State name="landscape" />
+        <s:State name="disabled" />
+        <s:State name="normal" />
+    </s:states>
+    
+    <!--- Defines the appearance of the SkinnableContainer class's background. 
-->
+    <s:Rect id="background" left="0" right="0" top="0" bottom="0" radiusX="10" 
radiusY="10">
+        <s:fill>
+            <!--- @private -->
+            <s:SolidColor id="bgFill" color="#FF0000"/>
+        </s:fill>
+    </s:Rect>
+    
+    <!--
+        Note: setting the minimum size to 0 here so that changes to the host 
component's
+        size will not be thwarted by this skin part's minimum size.   This is 
a compromise,
+        more about it here: http://bugs.adobe.com/jira/browse/SDK-21143
+    -->
+    <!--- @copy spark.components.SkinnableContainer#contentGroup -->
+    <s:Group id="contentGroup" 
+                        left.portrait="20" 
+                        right.portrait="20" 
+                        top.portrait="40" 
+                        bottom.portrait="40" 
+                        
+                        left.landscape="40" 
+                        right.landscape="40" 
+                        top.landscape="20" 
+                        bottom.landscape="20" 
+                        minWidth="0" 
+                        minHeight="0"
+                        width="100%" height="100%">
+        <s:layout>
+            <s:BasicLayout/>
+        </s:layout>
+    </s:Group>
+
+</s:Skin>

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/skins/MenuBarButtonSkin.mxml
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/skins/MenuBarButtonSkin.mxml 
b/Radii8Library/src/com/flexcapacitor/skins/MenuBarButtonSkin.mxml
new file mode 100644
index 0000000..41caa02
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/skins/MenuBarButtonSkin.mxml
@@ -0,0 +1,233 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+Licensed to the Apache Software Foundation (ASF) under one or more
+contributor license agreements.  See the NOTICE file distributed with
+this work for additional information regarding copyright ownership.
+The ASF licenses this file to You under the Apache License, Version 2.0
+(the "License"); you may not use this file except in compliance with
+the License.  You may obtain a copy of the License at
+
+http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+-->
+
+<!--- The default skin class for the Spark Button component.  
+
+       @see spark.components.Button
+        
+      @langversion 3.0
+      @playerversion Flash 10
+      @playerversion AIR 1.5
+      @productversion Flex 4
+-->
+<s:SparkButtonSkin xmlns:fx="http://ns.adobe.com/mxml/2009"; 
+             xmlns:s="library://ns.adobe.com/flex/spark" 
+             xmlns:fb="http://ns.adobe.com/flashbuilder/2009";
+             minWidth="21" minHeight="21" 
+             alpha.disabled="0.5">
+     
+    <fx:Metadata>
+        <![CDATA[ 
+        /** 
+         * @copy spark.skins.spark.ApplicationSkin#hostComponent
+         */
+        [HostComponent("spark.components.Button")]
+        ]]>
+    </fx:Metadata>
+    
+    <fx:Script fb:purpose="styling">
+        <![CDATA[         
+            import spark.components.Group;
+            /* Define the skin elements that should not be colorized. 
+            For button, the graphics are colorized but the label is not. */
+            static private const exclusions:Array = ["labelDisplay"];
+            
+            /** 
+             * @private
+             */     
+            override public function get colorizeExclusions():Array {return 
exclusions;}
+            
+            /**
+             * @private
+             */
+            override protected function initializationComplete():void
+            {
+                useChromeColor = true;
+                super.initializationComplete();
+            }  
+            
+            /**
+             *  @private
+             */
+            override protected function 
updateDisplayList(unscaledWidth:Number, unscaledHeight:Number) : void
+            {
+                var cr:Number = getStyle("cornerRadius");
+                
+                if (cornerRadius != cr)
+                {
+                    cornerRadius = cr;
+                    /*shadow.radiusX = cornerRadius;
+                    fill.radiusX = cornerRadius;
+                    lowlight.radiusX = cornerRadius;
+                    highlight.radiusX = cornerRadius;
+                    border.radiusX = cornerRadius;*/
+                }
+                /*
+                if (highlightStroke) highlightStroke.radiusX = cornerRadius;
+                if (hldownstroke1) hldownstroke1.radiusX = cornerRadius;
+                if (hldownstroke2) hldownstroke2.radiusX = cornerRadius;*/
+                
+                super.updateDisplayList(unscaledWidth, unscaledHeight);
+                               
+                               if (labelDisplay) {
+                                       Label(labelDisplay).setStyle("color", 
0xFFFFFF);
+                               }
+            }
+            
+            private var cornerRadius:Number = 2;
+                                 
+        ]]>        
+    </fx:Script>
+        
+    <!-- states -->
+    <s:states>
+        <s:State name="up" />
+        <s:State name="over" />
+        <s:State name="down" />
+        <s:State name="disabled" />
+    </s:states>
+    
+    <!-- layer 1: shadow -->
+    <!--- @private -->
+    <!--<s:Rect id="shadow" left="-1" right="-1" top="-1" bottom="-1" 
radiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0x000000" 
+                                 color.down="0xFFFFFF"
+                                 alpha="0.01"
+                                 alpha.down="0" />
+                <s:GradientEntry color="0x000000" 
+                                 color.down="0xFFFFFF" 
+                                 alpha="0.07"
+                                 alpha.down="0.5" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 2: fill -->
+    <!--- @private -->
+    <!--<s:Rect id="fill" left="1" right="1" top="1" bottom="1" radiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0xFFFFFF" 
+                                 color.over="0xBBBDBD" 
+                                 color.down="0xAAAAAA" 
+                                 alpha="0.85" />
+                <s:GradientEntry color="0xD8D8D8" 
+                                 color.over="0x9FA0A1" 
+                                 color.down="0x929496" 
+                                 alpha="0.85" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+
+    <!-- layer 3: fill lowlight -->
+    <!--- @private -->
+    <!--<s:Rect id="lowlight" left="1" right="1" top="1" bottom="1" 
radiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="270">
+                <s:GradientEntry color="0x000000" ratio="0.0" alpha="0.0627" />
+                <s:GradientEntry color="0x000000" ratio="0.48" alpha="0.0099" 
/>
+                <s:GradientEntry color="0x000000" ratio="0.48001" alpha="0" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 4: fill highlight -->
+    <!--- @private -->
+    <!--<s:Rect id="highlight" left="1" right="1" top="1" bottom="1" 
radiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0xFFFFFF"
+                                 ratio="0.0"
+                                 alpha="0.33" 
+                                 alpha.over="0.22" 
+                                 alpha.down="0.12"/>
+                <s:GradientEntry color="0xFFFFFF"
+                                 ratio="0.48"
+                                 alpha="0.33"
+                                 alpha.over="0.22"
+                                 alpha.down="0.12" />
+                <s:GradientEntry color="0xFFFFFF"
+                                 ratio="0.48001"
+                                 alpha="0" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 5: highlight stroke (all states except down) -->
+    <!--- @private -->
+    <!--<s:Rect id="highlightStroke" left="1" right="1" top="1" bottom="1" 
radiusX="2" excludeFrom="down">
+        <s:stroke>
+            <s:LinearGradientStroke rotation="90" weight="1">
+                <s:GradientEntry color="0xFFFFFF" alpha.over="0.22" />
+                <s:GradientEntry color="0xD8D8D8" alpha.over="0.22" />
+            </s:LinearGradientStroke>
+        </s:stroke>
+    </s:Rect>-->
+    
+    <!-- layer 6: highlight stroke (down state only) -->
+    <!--- @private -->
+    <!--<s:Rect id="hldownstroke1" left="1" right="1" top="1" bottom="1" 
radiusX="2" includeIn="down">
+        <s:stroke>
+            <s:LinearGradientStroke rotation="90" weight="1">
+                <s:GradientEntry color="0x000000" alpha="0.25" ratio="0.0" />
+                <s:GradientEntry color="0x000000" alpha="0.25" ratio="0.001" />
+                <s:GradientEntry color="0x000000" alpha="0.07" ratio="0.0011" 
/>
+                <s:GradientEntry color="0x000000" alpha="0.07" ratio="0.965" />
+                <s:GradientEntry color="0x000000" alpha="0.00" ratio="0.9651" 
/>
+            </s:LinearGradientStroke>
+        </s:stroke>
+    </s:Rect>-->
+    <!--- @private -->
+    <!--<s:Rect id="hldownstroke2" left="2" right="2" top="2" bottom="2" 
radiusX="2" includeIn="down">
+        <s:stroke>
+            <s:LinearGradientStroke rotation="90" weight="1">
+                <s:GradientEntry color="0x000000" alpha="0.09" ratio="0.0" />
+                <s:GradientEntry color="0x000000" alpha="0.00" ratio="0.0001" 
/>
+            </s:LinearGradientStroke>
+        </s:stroke>
+    </s:Rect>-->
+
+    <!-- layer 7: border - put on top of the fill so it doesn't disappear when 
scale is less than 1 -->
+    <!--- @private -->
+    <!--<s:Rect id="border" left="0" right="0" top="0" bottom="0" width="69" 
height="20" radiusX="2">
+        <s:stroke>
+            <s:LinearGradientStroke rotation="90" weight="1">
+                <s:GradientEntry color="0x000000" 
+                                 alpha="0.5625"
+                                 alpha.down="0.6375" />
+                <s:GradientEntry color="0x000000" 
+                                 alpha="0.75" 
+                                 alpha.down="0.85" />
+            </s:LinearGradientStroke>
+        </s:stroke>
+    </s:Rect>-->
+    
+    <!-- layer 8: text -->
+    <!--- @copy spark.components.supportClasses.ButtonBase#labelDisplay  -->
+    <s:Label id="labelDisplay"
+             textAlign="center"
+             maxDisplayedLines="1"
+             horizontalCenter="0" verticalCenter="1" verticalAlign="middle"
+             left="10" right="10" top="2" bottom="2">
+    </s:Label>
+    
+</s:SparkButtonSkin>

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/skins/MenuItemSkin.mxml
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/skins/MenuItemSkin.mxml 
b/Radii8Library/src/com/flexcapacitor/skins/MenuItemSkin.mxml
new file mode 100644
index 0000000..38764e4
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/skins/MenuItemSkin.mxml
@@ -0,0 +1,57 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+Licensed to the Apache Software Foundation (ASF) under one or more
+contributor license agreements.  See the NOTICE file distributed with
+this work for additional information regarding copyright ownership.
+The ASF licenses this file to You under the Apache License, Version 2.0
+(the "License"); you may not use this file except in compliance with
+the License.  You may obtain a copy of the License at
+
+http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+-->
+
+<!--- The wireframe skin class for menu items in the MX Menu component. 
+
+      @see mx.controls.Menu
+      @see mx.controls.MenuItem
+        
+      @langversion 3.0
+      @playerversion Flash 10
+      @playerversion AIR 1.5
+      @productversion Flex 4
+-->
+<s:Skin xmlns:fx="http://ns.adobe.com/mxml/2009"; 
xmlns:s="library://ns.adobe.com/flex/spark" 
+      minWidth="21" minHeight="21"
+      alpha.disabled="0.5">
+
+    <!-- states -->
+    <s:states>
+        <s:State name="up" />
+        <s:State name="over" />
+        <s:State name="down" />
+        <s:State name="disabled" />
+    </s:states>
+    
+    <!-- layer 1: fill -->
+    <s:Rect left="0" right="0" top="1" bottom="1" excludeFrom="up,disabled" >
+        <s:fill>
+            <s:SolidColor color="#5983f7" />
+        </s:fill>
+    </s:Rect>
+    
+    <!-- layer 2: fill highlight -->
+    <!--<s:Rect left="0" right="0" top="1" height="9" excludeFrom="up" >
+        <s:fill>
+            <s:SolidColor color="0xFFFFFF" alpha="0.33" />
+        </s:fill>
+    </s:Rect>-->
+    
+</s:Skin>

http://git-wip-us.apache.org/repos/asf/flex-radii8/blob/f370bfcf/Radii8Library/src/com/flexcapacitor/skins/PopUpButtonSkin.mxml
----------------------------------------------------------------------
diff --git a/Radii8Library/src/com/flexcapacitor/skins/PopUpButtonSkin.mxml 
b/Radii8Library/src/com/flexcapacitor/skins/PopUpButtonSkin.mxml
new file mode 100644
index 0000000..82a2dbf
--- /dev/null
+++ b/Radii8Library/src/com/flexcapacitor/skins/PopUpButtonSkin.mxml
@@ -0,0 +1,287 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+Licensed to the Apache Software Foundation (ASF) under one or more
+contributor license agreements.  See the NOTICE file distributed with
+this work for additional information regarding copyright ownership.
+The ASF licenses this file to You under the Apache License, Version 2.0
+(the "License"); you may not use this file except in compliance with
+the License.  You may obtain a copy of the License at
+
+http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+
+-->
+
+<!--- The Spark skin class for the MX PopUpButton component. 
+
+      @see mx.controls.PopUpButton
+        
+      @langversion 3.0
+      @playerversion Flash 10
+      @playerversion AIR 1.5
+      @productversion Flex 4
+-->
+<local:SparkSkinForHalo xmlns:fx="http://ns.adobe.com/mxml/2009"; 
xmlns:s="library://ns.adobe.com/flex/spark" 
+      xmlns:local="mx.skins.spark.*"
+      minWidth="21" minHeight="21"
+      alpha.disabled="0.5">
+    
+    <fx:Script>
+        /* Define the skin elements that should not be colorized. 
+           For button, the graphics are colorized but the arrow is not. */
+        static private const exclusions:Array = ["arrow"];
+        /**
+         *  @private
+         */
+        override public function get colorizeExclusions():Array {return 
exclusions;}
+        
+        /* Define the symbol fill items that should be colored by the 
"symbolColor" style. */
+        static private const symbols:Array = ["arrowFill1", "arrowFill2"];
+        /**
+         *  @private
+         */
+        override public function get symbolItems():Array {return symbols};
+
+        /* Define the border items.*/
+        //static private const borderItem:Array = ["borderEntry1", 
"borderEntry2"];
+        static private const borderItem:Array = [];
+        /**
+         *  @private
+         */
+        override protected function get borderItems():Array {return 
borderItem;}
+        
+        /**
+         * @private
+         */
+        override protected function initializationComplete():void
+        {
+            useChromeColor = true;
+            super.initializationComplete();
+        }
+        
+        /**
+         *  @private
+         */
+        override protected function updateDisplayList(unscaledWidth:Number, 
unscaledHeight:Number) : void
+        {
+            var cr:Number = getStyle("cornerRadius");
+            
+            if (cornerRadius != cr)
+            {
+                cornerRadius = cr;
+                /*shadow.radiusX = cornerRadius;
+                fill.topLeftRadiusX = cornerRadius;
+                fill.bottomLeftRadiusX = cornerRadius;
+                fill2.topRightRadiusX = cornerRadius;
+                fill2.bottomRightRadiusX = cornerRadius;
+                lowlight.radiusX = cornerRadius;
+                highlight.radiusX = cornerRadius;
+                border.radiusX = cornerRadius;*/
+            }
+                
+            //if (highlightStroke) highlightStroke.radiusX = cornerRadius;
+                
+            super.updateDisplayList(unscaledWidth, unscaledHeight);
+        }
+        
+        private var cornerRadius:Number = 2;
+    </fx:Script>
+    
+    <!-- states -->
+    <local:states>
+        <s:State name="up" />
+        <s:State name="over" stateGroups="overStates" />
+        <s:State name="down" stateGroups="downStates" />
+        <s:State name="disabled" />
+        <s:State name="popUpOver" stateGroups="overStates, popUpStates" />
+        <s:State name="popUpDown" stateGroups="downStates, popUpStates" />
+    </local:states>
+    
+    <!-- layer 1: shadow -->
+    <!--- @private -->
+    <!--<s:Rect id="shadow" left="-1" right="-1" top="-1" bottom="-1" 
radiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0x000000" 
+                               color.downStates="0xFFFFFF"
+                               alpha="0.01"
+                               alpha.downStates="0" />
+                <s:GradientEntry color="0x000000" 
+                               color.downStates="0xFFFFFF" 
+                               alpha="0.07"
+                               alpha.downStates="0.5" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 2: fill -->
+    <!--- @private -->
+    <!--<s:Rect id="fill" left="1" right="18" top="1" bottom="1" 
+            topLeftRadiusX="2" bottomLeftRadiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0xFFFFFF" 
+                                 color.over="0xBBBDBD" 
+                                 color.down="0xAAAAAA" 
+                                 alpha="0.85" />
+                <s:GradientEntry color="0xD8D8D8" 
+                                 color.over="0x9FA0A1" 
+                                 color.down="0x929496" 
+                                 alpha="0.85" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    <!--- @private -->
+    <!--<s:Rect id="fill2" width="18" right="1" top="1" bottom="1" 
+            topRightRadiusX="2" bottomRightRadiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0xFFFFFF" 
+                                 color.popUpOver="0xBBBDBD" 
+                                 color.popUpDown="0xAAAAAA" 
+                                 alpha="0.85" />
+                <s:GradientEntry color="0xD8D8D8" 
+                                 color.popUpOver="0x9FA0A1" 
+                                 color.popUpDown="0x929496" 
+                                 alpha="0.85" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 3: fill lowlight -->
+    <!--- @private -->
+    <!--<s:Rect id="lowlight" left="1" right="1" top="1" bottom="1" 
radiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="270">
+                <s:GradientEntry color="0x000000" ratio="0.0" alpha="0.0627" />
+                <s:GradientEntry color="0x000000" ratio="0.48" alpha="0.0099" 
/>
+                <s:GradientEntry color="0x000000" ratio="0.48001" alpha="0" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 4: fill highlight -->
+    <!--- @private -->
+    <!--<s:Rect id="highlight" left="1" right="1" top="1" bottom="1" 
radiusX="2">
+        <s:fill>
+            <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0xFFFFFF"
+                                 ratio="0.0"
+                                 alpha="0.33"
+                                 alpha.overStates="0.22" 
+                                 alpha.downStates="0.12"/>
+                <s:GradientEntry color="0xFFFFFF"
+                                 ratio="0.48"
+                                 alpha="0.33"
+                                 alpha.overStates="0.22" 
+                                 alpha.downStates="0.12"/>
+                <s:GradientEntry color="0xFFFFFF"
+                                 ratio="0.48001"
+                                 alpha="0" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 5: highlight stroke (all states except down) -->
+    <!--- @private -->
+    <!--<s:Rect id="highlightStroke"  left="1" right="1" top="1" bottom="1" 
radiusX="2" excludeFrom="downStates">
+        <s:stroke>
+            <s:LinearGradientStroke rotation="90" weight="1">
+                <s:GradientEntry color="0xFFFFFF" alpha.overStates="0.22" />
+                <s:GradientEntry color="0xD8D8D8" alpha.overStates="0.22" />
+            </s:LinearGradientStroke>
+        </s:stroke>
+    </s:Rect>-->
+    
+    <!-- layer 6: highlight stroke (down state only) -->
+    <!--- @private -->
+    <!--<s:Rect left="1" top="1" bottom="1" width="1" includeIn="down">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.07" />
+        </s:fill>
+    </s:Rect>
+    <s:Rect right="19" top="1" bottom="1" width="1" includeIn="down">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.07" />
+        </s:fill>
+    </s:Rect>
+    <s:Rect left="2" top="1" right="19" height="1" includeIn="down">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.25" />
+        </s:fill>
+    </s:Rect>
+    <s:Rect left="1" top="2" right="19" height="1" includeIn="down">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.09" />
+        </s:fill>
+    </s:Rect>
+    
+    <s:Rect right="17" top="1" bottom="1" width="1" includeIn="popUpDown">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.07" />
+        </s:fill>
+    </s:Rect>
+    <s:Rect right="1" top="1" bottom="1" width="1" includeIn="popUpDown">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.07" />
+        </s:fill>
+    </s:Rect>
+    <s:Rect width="16" top="1" right="2" height="1" includeIn="popUpDown">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.25" />
+        </s:fill>
+    </s:Rect>
+    <s:Rect width="17" top="2" right="1" height="1" includeIn="popUpDown">
+        <s:fill>
+            <s:SolidColor color="0x000000" alpha="0.09" />
+        </s:fill>
+    </s:Rect>-->
+    
+    <!-- layer 7: border - put on top of the fill so it doesn't disappear when 
scale is less than 1 -->
+    <!--- @private -->
+    <!--<s:Rect id="border" left="0" right="0" top="0" bottom="0" width="69" 
height="20" radiusX="2">
+        <s:stroke>
+            <s:LinearGradientStroke rotation="90" weight="1">
+                <s:GradientEntry id="borderEntry1" 
+                               alpha="0.5625"
+                               alpha.downStates="0.6375" />
+                <s:GradientEntry id="borderEntry2"  
+                               alpha="0.75" 
+                               alpha.downStates="0.85" />
+            </s:LinearGradientStroke>
+        </s:stroke>
+    </s:Rect>
+    <s:Rect right="18" top="1" bottom="1" width="1">
+        <s:fill>
+             <s:LinearGradient rotation="90">
+                <s:GradientEntry color="0x000000" 
+                               alpha="0.5625"
+                               alpha.downStates="0.6375" />
+                <s:GradientEntry color="0x000000" 
+                               alpha="0.75" 
+                               alpha.downStates="0.85" />
+            </s:LinearGradient>
+        </s:fill>
+    </s:Rect>-->
+
+    <!-- layer 8: arrow -->
+    <!--- @private -->
+    <s:Path right="6" verticalCenter="0" id="arrow"
+          data="M 4.0 4.0 L 4.0 3.0 L 5.0 3.0 L 5.0 2.0 L 6.0 2.0 L 6.0 1.0 L 
7.0 1.0 L 7.0 0.0 L 0.0 0.0 L 0.0 1.0 L 1.0 1.0 L 1.0 2.0 L 2.0 2.0 L 2.0 3.0 L 
3.0 3.0 L 3.0 4.0 L 4.0 4.0"
+                 visible="false" includeInLayout="false">
+        <s:fill>
+            <s:RadialGradient rotation="90" focalPointRatio="1">    
+                <!--- @private -->
+                <s:GradientEntry id="arrowFill1" color="0" alpha="0.6" />
+                <!--- @private -->
+                <s:GradientEntry id="arrowFill2" color="0" alpha="0.8" />
+            </s:RadialGradient>
+        </s:fill>
+    </s:Path>
+</local:SparkSkinForHalo>

Reply via email to