
registerType('appdoo', (function () { function Editor() {} var __super = setSupertypeFromDomain(Editor, 'ViewController', 'Core.UI');

	Object.defineProperty(Editor.prototype, "historyManager", {
	outlet: true, 
	synthesized: true, get:function () { return this._historyManager; }, set:function (v) {if (!Object.hasOwnProperty(this, "_historyManager")) Object.defineProperty(this, "_historyManager", { writable: true, configurable: true }); this._historyManager = v; }});
	

	Object.defineProperty(Editor.prototype, "inspector", {
	outlet: true, 
	synthesized: true, get:function () { return this._inspector; }, set:function (v) {if (!Object.hasOwnProperty(this, "_inspector")) Object.defineProperty(this, "_inspector", { writable: true, configurable: true }); this._inspector = v; }});
	

	Object.defineProperty(Editor.prototype, "overview", {
	outlet: true, 
	synthesized: true, get:function () { return this._overview; }, set:function (v) {if (!Object.hasOwnProperty(this, "_overview")) Object.defineProperty(this, "_overview", { writable: true, configurable: true }); this._overview = v; }});
	

	Object.defineProperty(Editor.prototype, "selection", {
	outlet: true, 
	synthesized: true, get:function () { return this._selection; }, set:function (v) {if (!Object.hasOwnProperty(this, "_selection")) Object.defineProperty(this, "_selection", { writable: true, configurable: true }); this._selection = v; }});
	

	Object.defineProperty(Editor.prototype, "searchField", {
	outlet: true, 
	synthesized: true, get:function () { return this._searchField; }, set:function (v) {if (!Object.hasOwnProperty(this, "_searchField")) Object.defineProperty(this, "_searchField", { writable: true, configurable: true }); this._searchField = v; }});
	

	Object.defineProperty(Editor.prototype, "contentFrameController", {
	outlet: true, 
	synthesized: true, get:function () { return this._contentFrameController; }, set:function (v) {if (!Object.hasOwnProperty(this, "_contentFrameController")) Object.defineProperty(this, "_contentFrameController", { writable: true, configurable: true }); this._contentFrameController = v; }});
	

	Object.defineProperty(Editor.prototype, "treeController", {
	outlet: true, 
	synthesized: true, get:function () { return this._treeController; }, set:function (v) {if (!Object.hasOwnProperty(this, "_treeController")) Object.defineProperty(this, "_treeController", { writable: true, configurable: true }); this._treeController = v; }});
	

	Object.defineProperty(Editor.prototype, "mainSplitView", {
	outlet: true, 
	synthesized: true, get:function () { return this._mainSplitView; }, set:function (v) {if (!Object.hasOwnProperty(this, "_mainSplitView")) Object.defineProperty(this, "_mainSplitView", { writable: true, configurable: true }); this._mainSplitView = v; }});
	

	Object.defineProperty(Editor.prototype, "devicePopupButton", {
	outlet: true, 
	synthesized: true, get:function () { return this._devicePopupButton; }, set:function (v) {if (!Object.hasOwnProperty(this, "_devicePopupButton")) Object.defineProperty(this, "_devicePopupButton", { writable: true, configurable: true }); this._devicePopupButton = v; }});
	

	Object.defineProperty(Editor.prototype, "rightSplitView", {
	outlet: true, 
	synthesized: true, get:function () { return this._rightSplitView; }, set:function (v) {if (!Object.hasOwnProperty(this, "_rightSplitView")) Object.defineProperty(this, "_rightSplitView", { writable: true, configurable: true }); this._rightSplitView = v; }});
	
	
	Object.defineProperty(Editor.prototype, "outlineViewContainer", {
	outlet: true, 
	synthesized: true, get:function () { return this._outlineViewContainer; }, set:function (v) {if (!Object.hasOwnProperty(this, "_outlineViewContainer")) Object.defineProperty(this, "_outlineViewContainer", { writable: true, configurable: true }); this._outlineViewContainer = v; }});
	

	Object.defineProperty(Editor.prototype, "visibleOutlineView", {
		get: function () {
			if (this.elementListIsVisible) return this.outlineViewContainer.subviews[0];
		}});
	

	Object.defineProperty(Editor.prototype, "projectScenesController", {
	outlet: true, 
	synthesized: true, get:function () { return this._projectScenesController; }, set:function (v) {if (!Object.hasOwnProperty(this, "_projectScenesController")) Object.defineProperty(this, "_projectScenesController", { writable: true, configurable: true }); this._projectScenesController = v; }});
	

	Object.defineProperty(Editor.prototype, "editorSourceView", {
	outlet: true, 
	synthesized: true, get:function () { return this._editorSourceView; }, set:function (v) {if (!Object.hasOwnProperty(this, "_editorSourceView")) Object.defineProperty(this, "_editorSourceView", { writable: true, configurable: true }); this._editorSourceView = v; }});
	
	
	Object.defineProperty(Editor.prototype, "dataContextsController", {
	outlet: true, 
	synthesized: true, get:function () { return this._dataContextsController; }, set:function (v) {if (!Object.hasOwnProperty(this, "_dataContextsController")) Object.defineProperty(this, "_dataContextsController", { writable: true, configurable: true }); this._dataContextsController = v; }});
	

	Object.defineProperty(Editor.prototype, "newItemListDataSource", {
	outlet: true, 
	synthesized: true, get:function () { return this._newItemListDataSource; }, set:function (v) {if (!Object.hasOwnProperty(this, "_newItemListDataSource")) Object.defineProperty(this, "_newItemListDataSource", { writable: true, configurable: true }); this._newItemListDataSource = v; }});
	
	
Editor.prototype.contextMenuForSelection = function Editor__contextMenuForSelection(selection) {
	
		if (selection.length === 1 ||
			selection[0] === this.editedView ||
    		selection[0] === this.navigationObjectsNode.representedObject ||
    		selection[0] === this.objectsNode.representedObject ||
    		selection[0] === this.appObjectsNode.representedObject ||
    		selection[0] === this.editedScene.statusBarBackgroundView ||
    		selection[0] === this.editedScene.navigationBar ||
    		selection[0] === this.editedScene.viewController.tabBarItem ||
    		selection[0] === this.editedScene.tabBarController.tabBar ||
    		selection[0] === this.fileReferencesNode.representedObject ||
    	   (selection[0].node && selection[0].node.parentNode.parentNode === this.navigationObjectsNode)) {
			return;
		}
		
		var t = {
		  "$type" : "Menu",
		  "$domain" : "Core.UI",
		  "$id" : "contextMenuForSelection",
		  "items" : [
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Edit"),
			  "tag" : 0,
			  "targetMethod" : "editGroupFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Ungroup"),
			  "tag" : 1,
			  "targetMethod" : "ungroupFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ],
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Group"),
			  "tag" : 2,
			  "targetMethod" : "groupFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "separator" : true,
			  "tag": 100001,
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Unlock"),
			  "tag" : 700,
			  "targetMethod" : "unlockFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Lock"),
			  "tag" : 701,
			  "targetMethod" : "lockFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "separator" : true,
			  "tag": 100002,
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Cut"),
			  "tag" : 3,
			  "targetMethod" : "cutFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Copy"),
			  "tag" : 4,
			  "targetMethod" : "copyFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Paste"),
			  "tag" : 5,
			  "targetMethod" : "pasteFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Duplicate"),
			  "targetMethod" : "duplicateFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "title" : LocalizedString("Delete"),
			  "tag" : 6,
			  "targetMethod" : "deleteFromContextMenu",
			  "connections" : [
				{
				  "key" : "target",
				  "destination" : "editor"
				}
			  ]
			},
			{
			  "$type" : "MenuItem",
			  "$domain" : "Core.UI",
			  "separator" : true,
			},
			{
			  "$type": "MenuItem",
			  "$domain": "Core.UI",
			  "title": LocalizedString("Move Forward"),
			  "target": this,
			  "targetMethod": "sendForwardFromContextMenu",
			  "enabled": this.itemsCanBeSentForward(this.selectionForContextMenu)
			},
			{
			  "$type": "MenuItem",
			  "$domain": "Core.UI",
			  "title": LocalizedString("Move Backward"),
			  "target": this,
			  "targetMethod": "sendBackwardFromContextMenu",
			  "enabled": this.itemsCanBeSentBackward(this.selectionForContextMenu)
			},
		  ]
		};
		
		var menu = this.context.decodeObjectTree(t);
		
		if (selection.length === 1 && selection[0].UTI === 'appdoo.ResourceReference') {
			selection[0].addFileItemsToMenu(menu);
		}

		return menu;
};
	



// role BasicObject (Core) 
		
Editor.prototype.destroy = function Editor_destroy() {
			var node = this.view.DOMNode;
			if (node.parentNode) {
				node.parentNode.removeChild(node);
			}

			this.closeItem();
			this.removeWindowEvents();
			__super.prototype.destroy.call(this);
			userFonts = null;};
		
	
	



	

// role MainViewController (appdoo.appdooContext) 

Editor.prototype.performAfterLoading = function Editor_performAfterLoading(callback) {
		
			if (this.view === undefined) {
				if (!this.loadView()) return;
				this.view.hidden = true;
				document.body.appendChild(this.view.DOMNode);
				this.view.size = {
					width: window.innerWidth,
					height: window.innerHeight
				};
			}
			
			callback();
	};
		

Editor.prototype.validateToolbarItem = function Editor_validateToolbarItem(identifier) {

			if (identifier === 'sendForward')
				return this.selectionCanBeSentForward();

			if (identifier === 'sendBackward')
				return this.selectionCanBeSentBackward();

			if (identifier === 'exportToXcode')
				return true;

			if (identifier === 'goToOverview')
				return true;
			
			return false;};
		
		
Editor.prototype.validateMenuItem = function Editor_validateMenuItem(tag) {
		
			var result = false;

			switch (tag) {
				case 20001:
					result = this.selectionCanBeSentToFront();
					break;
				case 20002:
					result = this.selectionCanBeSentToBack();
					break;
				case 20003:
					result = this.selectionCanBeSentForward();
					break;
				case 20004:
					result = this.selectionCanBeSentBackward();
					break;
				case 20005:
					result = this.selectionCanBeGrouped();
					break;
				case 20006:
					result = this.selectionCanBeUngrouped();
					break;
				case 20007:
				case 20008:
				case 20009:
				case 20010:
				case 20011:
				case 20012:
					result = this.selection.items.length > 1;
					break;
				case 200100: 
					result = this.context.projectContext.simulatedDeviceIsIPhone;
					break;
				case 200200:
					result = this.contentFrameController.canZoomIn();
					break;
				case 200201:
					result = this.contentFrameController.canZoomOut();
					break;
				case 200202:
					result = this.contentFrameController.contentScale !== 1;
					break;
				case 500000:
					result = true;
					break;
			}

			return result;};
		

	
	


	

// role ViewDelegate (Core.UI) 
	
Editor.prototype.viewDidLoad = function Editor_viewDidLoad(view) {

			__super.prototype.viewDidLoad.call(this, view);

			if (view !== this.view) return;

			this.contentFrameController.viewDidLoadCallOnce();
			this.addDefaultContextMenuToView(this.contentFrameController.view, true);

			
			if (!this.context.isOffscreen) {
				var helperViewWidth = 270;
				var delta = helperViewWidth-210;
				if (delta) {
					this.mainSplitView.subviews[0].size.width += delta;
					this.mainSplitView.subviews[1].size.width -= delta;
		
					this.rightSplitView.subviews[0].size.width -= delta;
					this.rightSplitView.subviews[1].size.width += delta;
				}
			}

			setTimeout(function () { this.context.preloadOverview(); }.bind(this), 200);
			};
		

		var didAppear;

Editor.prototype.viewDidAppear = function Editor_viewDidAppear() {
			if (didAppear) return; didAppear = true;
	
			this.addWindowEvents();

			if (this.editedViewController)
				this.context.prepareForUndoManagerWithID(this.editedViewController.$id);

			if (this.manipulator !== undefined)
				this.manipulator.viewDidAppear();
};
		
		
Editor.prototype.viewDidDisappear = function Editor_viewDidDisappear() {
			if (!didAppear) return; didAppear = false;

			this.removeWindowEvents();

			if (this.manipulator !== undefined)
				this.manipulator.viewDidDisappear();
			
			this.closeItem();
			};
		
		

	


	
	
// role ProjectItemEditor 

Editor.prototype.openItem = function Editor_openItem(item, options) {

			if (!options) options = {};

			if (!options.keepHistory) this.sceneToGoBack = null;

			if (!item || !item.UTI || item.UTI !== 'appdoo.iOS.Scene') {
				console.warn('Trying to open data that is not a Scene (not supported).', item);
				console.trace();
				return;
			}

			if (item.$id === undefined) {
				console.warn('Cannot edit something without an id.');
				return;
			}

			if (this.editedScene) this.closeItem();
				
			this.isOpening = true;
			this.beginEditingScene(item);
			this.isOpening = false;
			
			if (!this.context.isOffscreen)
				this.historyManager.push(item);
	};
		

Editor.prototype.closeItem = function Editor_closeItem(skipSave) {
		
			if (skipSave !== true) this.saveItem();
			this.endEditingView();
			this.endEditingScene();
	};
		
		
Editor.prototype.getSelectedObjectIDs = function Editor__getSelectedObjectIDs() {
			var selectedObjectIDs = this.treeController.selectedValues.map(function (item) {
				if (item.identify)
					return item.identify();
			});
			return selectedObjectIDs;};
		

Editor.prototype.restoreSelection = function Editor__restoreSelection(ids, silent) {

			this.treeController.beginSelectionChange();
			this.treeController.unselectAll();
			if (Array.isArray(ids)) ids.every(function (id) {
				var item = this.context.projectContext.globals[id];
				if (!item) {
					setTimeout(function () {
				if (!item) item = this.context.projectContext.connectableObjects[id];
						this.treeController.selectValue(item, this);
					}.bind(this), 500);
				}
				this.treeController.selectValue(item, this);return true; }, this);
			
			if (silent) this.treeController.selectionModeChange--;
			else this.treeController.commitSelectionChange(this.inspector);};
		
		
		
		
		
		var selectedObjectIDs, editedSubview;
Editor.prototype.pauseSubviewEditing = function Editor_pauseSubviewEditing() {
			selectedObjectIDs = this.getSelectedObjectIDs();
			editedSubview = this.editedSubview;
			if(this.editedScene !== undefined && this.editedScene.selectedObjectIDs !== undefined) {
				this.editedScene.selectedObjectIDs = selectedObjectIDs;
			}
			this.endEditingSubview();};
		
		
Editor.prototype.resumeSubviewEditing = function Editor_resumeSubviewEditing() {
			if (this.editedSubview !== editedSubview) {
				this.beginEditingSubview(editedSubview);
			}
			this.restoreSelection(selectedObjectIDs, true);

			selectedObjectIDs = null;
			editedSubview = null;};
		
		
Editor.prototype.saveItem = function Editor_saveItem() {
			if (!this.editedScene) return;
			this.isSaving = true;
			
			
			this.pauseSubviewEditing();
			
			if (Array.isArray(this.stateModifiers)) this.stateModifiers.every(function (obj) {
				obj.disableState();return true; }, this);
			

			
			
			
			
			
			
			
			this.editedScene.viewController.saveView();

			

			
			
			this.editedScene.navigationObjectsNodeIsExpandedInEditorOutline = this.navigationObjectsNode.representedObject.isExpandedInEditorOutline;
			this.editedScene.sceneObjectsNodeIsExpandedInEditorOutline = this.objectsNode.representedObject.isExpandedInEditorOutline;

			
			

			setTimeout(function () {
				if (this.editedScene && this.editedScene.viewController) {
					this.context.captureProjectItemImage(this.editedScene.viewController.$id, true);
				}
			}.bind(this), 1);
			this.context.captureProjectItemImage(this.editedScene.viewController.$id);
			
			
			this.resumeSubviewEditing();

			if (Array.isArray(this.stateModifiers)) this.stateModifiers.every(function (obj) {
				obj.enableState();return true; }, this);
			
			this.isSaving = false;
};
		

		Object.defineProperty(Editor.prototype, "editedView", {
			get: function () {
				return this._editedView;
			}});
		

		Object.defineProperty(Editor.prototype, "editedViewController", {
			get: function () {
				if (this.editedScene) return this.editedScene.viewController;
			}});
		

		Object.defineProperty(Editor.prototype, "objectsNode", {
			get: function () {
				if (this.editedScene) return this.editedScene.objectsNode;
			}});
		

		Object.defineProperty(Editor.prototype, "navigationObjectsNode", {
			get: function () {
				if (this.editedScene) return this.editedScene.navigationObjectsNode;
			}});
		
		
Editor.prototype.changeEditedViewController = function Editor_changeEditedViewController(popUpButton) {
			this.openItemWithID(popUpButton.value);};
		

	


	

	var isListening;
Editor.prototype.beginEditingScene = function Editor__beginEditingScene(scene) {

		this.editedScene = scene;
		this.lastEditedSceneID = scene.$id;
	
		
		var um = this.context.undoManager;
		if (um) um.disableRegistration();

		this.addGlobalObjectsNode();
		this.addFileReferencesNode();

		this.registerItem(scene, this.treeController.rootNode);

		
		this.contentFrameController.editorDidLoadScene(scene);

		
		scene.prepareTreeControllerForScene();

		
		
		this.beginEditingView(scene.viewController.view);

		scene.registerObjectBindings();

		if (!this.context.isOffscreen) {
		
			this.observeObject(this.treeController);

			
			if (scene.selectedObjectIDs) {
				this.restoreSelection(scene.selectedObjectIDs);
			}
	
			if (!this.selection.items.length) {
				this.selection.items = [scene];
			}

			
			this.context.prepareForUndoManagerWithID(scene.$id);

			if (um) um.enableRegistration();
			
			if (!isListening) {
				isListening = true;
				this.listen(this.context.undoManager, 'performChange', this.undoManagerWillPerformUndo.bind(this));
				this.listen(this.context.undoManager, 'registerChange', this.undoManagerDidRegisterChange.bind(this));
			}
			
			this.updateLayout();
			this.newItemsList.reloadData();
		
		}
};
	
	
Editor.prototype.objectsGroupAcceptsMemberWithUTI = function Editor_objectsGroupAcceptsMemberWithUTI(uti, p, obj) {
	
		if (!uti) return false;
		if (!p) p = getType(uti);
		if (isKindOfType(p, getType('appdoo.ResourceReference'))) return false;
		if (isKindOfType(p.prototype, getType('Core.UI.View'))) return false;
		if (p && p.prototype && p.prototype.instancesCanBeLocal) return p.prototype.instancesCanBeLocal(obj);
		return p !== undefined;};
	

Editor.prototype.globalObjectsGroupAcceptsMemberWithUTI = function Editor_globalObjectsGroupAcceptsMemberWithUTI(uti, obj) {

		if (!uti) return false;
		var p = getType(uti);
		if (p && p.prototype && p.prototype.instancesCanBeGlobal) {
			return p.prototype.instancesCanBeGlobal(obj);
		}
		if (!this.objectsGroupAcceptsMemberWithUTI(uti, p, obj)) return false;
		return true;};
	
	
Editor.prototype.addGlobalObjectsNode = function Editor__addGlobalObjectsNode() {
	
		if (this.appObjectsNode) return;

		var appObjectsNode = createComponentFromDomain('GlobalObjectsTreeNode', 'appdoo', this.context, {
			scene: this.editedScene,
			representedObject: {
				readableValue: LocalizedString('Global Objects'),
				outlineIconURL: 'Resources/GlobalObjects.png',
				get: function (keyPath) { return this[keyPath]; },
				isExpandedInEditorOutline: this.context.projectContext.metadata.editorAppearance.globalObjectsNodeIsExpandedInEditorOutline === false ? false:true,
				acceptsMemberWithUTI: function (uti, obj) {
					return this.globalObjectsGroupAcceptsMemberWithUTI(uti, obj);
				}.bind(this),
				UTI: ''
			}
		});
		appObjectsNode.representedObject.node = appObjectsNode;
	
		this.appObjectsNode = appObjectsNode;

		if (Array.isArray(this.context.projectContext.objects)) this.context.projectContext.objects.every(function (obj) {
			var node = appObjectsNode.addChildNodeWithRepresentedObject(obj);
			Object.defineProperty(obj, 'node', { value: node, configurable: true });

			this.registerItem(obj);
			if (obj.addObserver)
				obj.addObserver(this);return true; }, this);
		
	};
	
	
Editor.prototype.addFileReferencesNode = function Editor__addFileReferencesNode() {
	
		if (this.fileReferencesNode) return;
	

		var fileReferencesNode = createComponentFromDomain('FileReferencesTreeNode', 'appdoo', this.context, {
			scene: this.editedScene,
			representedObject: {
				readableValue: LocalizedString('Files'),
				outlineIconURL: 'Resources/FileReferencesFolder.png',
				get: function (keyPath) { return this[keyPath]; },
				isExpandedInEditorOutline: this.context.projectContext.metadata.editorAppearance.fileReferencesNodeIsExpandedInEditorOutline !== false,
				acceptsMemberWithUTI: function (uti) {
					return isKindOfType(getType(uti), getType('appdoo.ResourceReference'));
				},
				UTI: ''
			}
		});
	
		this.fileReferencesNode = fileReferencesNode;
		

		if (Array.isArray(this.context.projectContext.fileReferences)) this.context.projectContext.fileReferences.every(function (obj) {
			var node = fileReferencesNode.addChildNodeWithRepresentedObject(obj);
			Object.defineProperty(obj, 'node', { value: node, configurable: true });

			this.registerItem(obj);
			if (obj.addObserver)
				obj.addObserver(this);return true; }, this);
		
	};
	
	
Editor.prototype.endEditingScene = function Editor__endEditingScene() {

		this.unlisten(this.context.undoManager, 'performChange');
		this.unlisten(this.context.undoManager, 'registerChange');
		isListening = false;

		this.unobserveObject(this.treeController);

		var scene = this.editedScene; if (!scene) return;

		
		this.unregisterItem(scene, true);
		
		scene.unregisterObjectBindings();

		this.contentFrameController.editorWillUnloadScene(scene);

		if (this.dataContextsController) {

			if (Array.isArray(clone(this.dataContextsController.contents))) clone(this.dataContextsController.contents).every(function (ctx) {
				
				if (this.context.projectContext.objects.indexOf(ctx.dataSource) !== -1) return true;

				
				if (ctx.dataSource) {
					if (isKindOfType(ctx.dataSource, getType('info.appdoo-mac.DataProvider'))) {
						if (this.context.projectContext.objects.indexOf(ctx.dataSource.object) !== -1) {
							return true;
						}
					}
				}
				
				this.dataContextsController.removeValue(ctx);return true; }, this);
			
		}
		
		delete this.editedView;
		delete this.editedSubview;
		delete this.editedScene;
		
		this.treeController.clear();
		this.appObjectsNode.parentNode = null;
		this.fileReferencesNode.parentNode = null;
		this.selection.replaceWithData([],this);
		
		
		if (Array.isArray(scene.objects)) scene.objects.every(function (obj) {
			if (Array.isArray(obj.bindings)) obj.bindings.every(function (binding) {
				delete binding.destinationObject;return true; }, this);
			return true; }, this);
		

		this.contentFrameController.editorDidUnloadScene(scene);

	};
	
	
Editor.prototype.loadDataContext = function Editor__loadDataContext(a) {
		
		if (!a) return;
	
		if (Array.isArray(a)) a.every(function (id) {
			var dataSource = this.context.projectContext.getLivingDataSourceWithId(id);
			if (dataSource) {
				dataSource.addObserver(this);
				dataSource.reload();
			}return true; }, this);
		};
	
	
Editor.prototype.setEditedViewControllerDataContextFromDataSource = function Editor__setEditedViewControllerDataContextFromDataSource(dataSourceId) {
		if (this.editedViewControllerDataContext) {
			this.popDataContextForDataSource(this.editedViewControllerDataContext.dataSource);
			delete this.editedViewControllerDataContext;
		}
		
		if (!dataSourceId) return;

		var dataSource = this.context.projectContext.getLivingDataSourceWithId(dataSourceId);
		
		if (!dataSource) return;
		
		dataSource.addObserver(this);
		dataSource.reload();};
	
	
Editor.prototype.dataSourceDidLoad = function Editor_dataSourceDidLoad(dataSource) {
		var ctx = this.pushDataContextForDataSource(dataSource);
		if (!ctx) ctx = {dataSource:dataSource};
		return this.applyDynamicBindings(ctx);
		};
	


	
	
Editor.prototype.beginEditingView = function Editor__beginEditingView(view) {
		
		this._editedView = this.editedSubview = view;

		
		if (this.editedViewControllerDataContext)
			this.applyDynamicBindings(this.editedViewControllerDataContext);

		var node = this.viewNode;
		this.registerItem(view, node);

		
		this.manipulator = createComponentFromDomain("Manipulator", "appdoo", this.context, {
			delegate: this,
			frameView: this.contentFrameController.view,
			contentWrapper: this.contentFrameController.contentWrapper,
			overlayView: this.contentFrameController.overlayView,
			contentScale: this.contentFrameController.contentScale,
			editedView: view,
			observableItemsController: this.treeController,
			showGuidelines: true,
			scrollWhenSelecting: true,
			useKeyEvents: true,
			useContextMenu: true})
		;
		
		
		if (Array.isArray(view.subviews)) view.subviews.every(function (subview) {
			this.registerItem(subview, this.treeController.nodeForRepresentedObject(subview));return true; }, this);
		

		
		this.registerViewAsDropTarget(view);
		};
	
	
Editor.prototype.addLayoutResolverForView = function Editor__addLayoutResolverForView(view, onlyLayoutNoProperty) {

		var layoutResolver = createComponentFromDomain("LayoutResolver", "appdoo.Editor", this.context, {
			view: view})
		;
		
		if (!onlyLayoutNoProperty) {
			if (view.layoutResolver) view.layoutResolver.destroy();
			Object.defineProperty(view, 'layoutResolver', { value: layoutResolver, configurable: true });
		}

		if (onlyLayoutNoProperty || this.shoudUpdateLayout) {
			layoutResolver.updateLayoutNow();
			this.shoudUpdateLayout = false;
		}
	};
	

Editor.prototype.resolveLayoutInView = function Editor__resolveLayoutInView(view) {
		this.addLayoutResolverForView(view, true);};
	
	
Editor.prototype.endEditingView = function Editor__endEditingView() {

		this.endEditingSubview();
		this.unregisterViewAsDropTarget(this._editedView);
		
		if (this.manipulator) {
			this.manipulator.destroy();
			delete this.manipulator;
		}
};
	
	
Editor.prototype.selectionEditDefault = function Editor__selectionEditDefault(e) {

		var items = this.selection.items;

		if (items.length !== 1)
			return;

		if (items[0] === this.editedViewController) {
			if (this.contentFrameController.navigationBarVisible)
				return this.contentFrameController.navigationBar.editDefault(this);
			return;
		}

		if (items[0].nameIsEditable && (!items[0].editDefault || e.altKey)) {
			if (this.visibleOutlineView) {
				var row = this.visibleOutlineView.rowForItem(items[0].node);
				var label = row.contentView.subviews[1];
				this.editNameFromOutlineCellLabel(e, label);
				return true;
			}
		}

		if (items[0].editDefault)
			return items[0].editDefault(this);
};
	
	

	

Editor.prototype.registerItem = function Editor_registerItem(item, node) {
	
		if (!item) return;

		if (!node) {
			node = this.treeController.nodeForRepresentedObject(item);
		}
		
		if (item.addObserver) item.addObserver(this);
		
		if (item._isRegistered) return;
		Object.defineProperty(item, '_isRegistered', { value: true, writable:true });
		
		
		this.injectSpecialMethodsToEditedObject(item);
	
		
		if (node) Object.defineProperty(item, 'node', { value: node, configurable: true });
		
		
		this.context.addDataControllerToObject(item, this);
		this.observeObject(item.dataController);

		
		if (item.prepareForEditor !== undefined) {
			item.prepareForEditor(this);
		}		
		
		
		this.context.projectContext.registerGlobal(item.identify(), item);
};
	
	
Editor.prototype.unregisterItem = function Editor_unregisterItem(item, sender, isClosing) {

		this.unobserveObject(item);
		if (item.removeObserver) item.removeObserver(this);

		if (!item._isRegistered) return;
		item._isRegistered = false;

		if (!item.node) {
			console.warn('unregisterItem(): This item is missing the node property:', item);
			console.trace();
			return;
		}
		
		if (item.unprepareForEditor) item.unprepareForEditor(this);

		if (sender === this && !isClosing) {
			this.treeController.removeValue(item, this);
		}

		if (item.dataController) {
			this.unobserveObject(item.dataController);
			item.dataController.destroy();
			delete item.dataController;
		}
		else {
			console.warn('The item being unregistered had no data controller.', item);
		}

		this.context.projectContext.unregisterGlobal(item.identify());
};
	
	
Editor.prototype.itemShouldBeFileReference = function Editor__itemShouldBeFileReference(item) {
		return (isKindOfType(getType(item.UTI), getType('appdoo.ResourceReference')));};
	
	
Editor.prototype.registerInsertedItem = function Editor__registerInsertedItem(item, setSelected, parentNode, index, indexIsInverse) {
	
		if (item._isRegistered) return;

		var itemIsAView = isKindOfType(item, getType('Core.UI.View'));
		if (itemIsAView && !item.autoresizingMask) {
			item.autoresizingMask = 36;
		}
		
		if (this.editedView) {
			if (!parentNode) {
			
				if (itemIsAView) {
					parentNode = this.editedSubview.node;
				}
				else {
					if (this.itemShouldBeFileReference(item))
						parentNode = this.fileReferencesNode;
					else {
						parentNode = this.preferredObjectNodeForItemWithUTI(item.UTI, item);
						if (!parentNode) {
							parentNode = this.objectsNode;
						}
					}
				}
			
				
			}
			
		}

		var indexForInsertion = 0; 
		if (!itemIsAView || item.isStaticCell) indexForInsertion = parentNode.childNodes.length;
		
		var inverseIndex = isNaN(index) ? indexForInsertion : parentNode.childNodes.length-index;
		
		
		
		if (indexIsInverse) { var _i = inverseIndex; inverseIndex = index; index = _i; }
		
		if (typeof index !== 'number' && parentNode) {
			index = parentNode.childNodes.length;
		}

		if (itemIsAView && !item.superview) {
			if (item.isStaticCell) {
				if (parentNode.representedObject.addCell)
					parentNode.representedObject.addCell(item, inverseIndex);
			}
			else {
			if(parentNode.representedObject.insertSubviewAtIndex)
				parentNode.representedObject.insertSubviewAtIndex(item, index);
			}
		}

		if (!itemIsAView) {
			if (parentNode === this.objectsNode)
				this.editedScene.addObject(item);
			else if (parentNode === this.appObjectsNode)
				this.context.projectContext.addObject(item);
			else if (parentNode === this.fileReferencesNode)
				this.context.projectContext.addFileReference(item);

			this.checkSpecialNodes();

		}

		var node = createComponentFromDomain("TreeNode", "Core", this.context, {
			controller: this.treeController,
			representedObject: item,
			parentNode: parentNode})
		;

		Object.defineProperty(item, 'node', { value: node, configurable: true });
	
		if (itemIsAView)
			parentNode.insertChildNodeAtIndex(node, inverseIndex);
		else
			parentNode.insertChildNodeAtIndex(node, index);

		this.registerItem(item, node);

		if (setSelected) {
			setTimeout(function () {
				this.treeController.beginSelectionChange();
				this.treeController.unselectAll();
				this.treeController.selectValue(item, this);
				this.treeController.commitSelectionChange(this.manipulator);
			}.bind(this), 1);
		}
		
		if (item.editorDidInsertThis)
			item.editorDidInsertThis(this);
		
		return node;};
	
	
Editor.prototype.preferredObjectNodeForItemWithUTI = function Editor__preferredObjectNodeForItemWithUTI(uti, item) {

		if (this.objectsNode.representedObject.acceptsMemberWithUTI(uti, item)) {
			return this.objectsNode;
		}

		if (this.appObjectsNode.representedObject.acceptsMemberWithUTI(uti, item)) {
			return this.appObjectsNode;
		}
};
	

// role ObjectControllerUndoDelegate (Core) 
	
Editor.prototype.objectControllerDidUndoChange = function Editor_objectControllerDidUndoChange(oc, change) {

			if (this.collectUndoDataTimer === undefined) {

				this.collectUndoDataTimer = setTimeout(function () {

					this.refreshInspector();
					delete this.collectUndoDataTimer;

				}.bind(this), 1);

			}
			};
		
		
	
	

	
	
Editor.prototype.applyDynamicBindings = function Editor__applyDynamicBindings(dataContext) {

		var ds = dataContext ? dataContext.dataSource : null;

		if (!this.editedScene) return;

		this.editedScene.applyBindings(false, ds);

		if (this.editedScene.navigationBar)
			this.editedScene.navigationBar.applyBindings();
	
		if (this.editedView) {
			this.applyDynamicBindingsInView(dataContext, this.editedScene.viewController.view);
			this.updateLayout();
		}
		
		if (Array.isArray(this.editedScene.objects)) this.editedScene.objects.every(function (obj) {
			obj.applyBindings(false, ds);return true; }, this);
		
};
	

Editor.prototype.applyDynamicBindingsInView = function Editor__applyDynamicBindingsInView(dataContext, view) {
	
		if (!view) return;

		if (Array.isArray(view.subviews)) view.subviews.every(function (subview) {
		
			subview.applyBindings();
			this.applyDynamicBindingsInView(dataContext, subview);
return true; }, this);
		
};
	


	
	
Editor.prototype.positionForInsertion = function Editor__positionForInsertion(size) {
	
		if (!size) return;
	
		
		
		if (size.width >= this.editedSubview.size.width ||
			size.height >= this.editedSubview.size.height)
			return {
				left: ((this.editedSubview.size.width-size.width)/2)|0,
				top: ((this.editedSubview.size.height-size.height)/2)|0,
			};
		
		if (this.isInSubviewEditingMode && this.editedSubview.size.height < 100)
			return {
				left: this.suggestedMinimumLeftPosition,
				top: ((this.editedSubview.size.height-size.height)/2)|0
			};
	
		if (this.editedSubview.lastInsertionPosition === undefined) {
			Object.defineProperty(this.editedSubview, 'lastInsertionPosition', {
				value: {
					left: this.suggestedMinimumLeftPosition,
					top: this.suggestedMinimumTopPosition
				}
			});
		}
		else {
			this.editedSubview.lastInsertionPosition.left += 10;
			this.editedSubview.lastInsertionPosition.top += 10;
			
			if (this.editedSubview.lastInsertionPosition.left + size.width >
				this.editedSubview.size.width)
				this.editedSubview.lastInsertionPosition.left = 10;

			if (this.editedSubview.lastInsertionPosition.top + size.height >
				this.editedSubview.size.height)
				this.editedSubview.lastInsertionPosition.top = this.suggestedMinimumTopPosition;
		}
		
		return this.editedSubview.lastInsertionPosition;
};
	
	
	Object.defineProperty(Editor.prototype, "suggestedMinimumTopPosition", {
		get: function () {
			var y = 10;
			if (!this.isInSubviewEditingMode && this.editedScene.e_showsNavigationBar && this.editedScene.navigationBar.translucent) {
				y += this.editedScene.navigationBar.size.height;
			}
			else if (this.context.projectContext.simulatedSystemVersion >= 7) y = 15;
			return y;
		}});
	

	Object.defineProperty(Editor.prototype, "suggestedMinimumLeftPosition", {
		get: function () {
			if (this.context.projectContext.simulatedSystemVersion >= 7) return 15;
			return 10;
		}});
	


	

// role SubviewEditingModeController 
	
Editor.prototype.beginEditingSubview = function Editor_beginEditingSubview(subview) {
		
			if (this.editedSubview === subview) return false;
			if (!(isKindOfType(subview, getType('Core.UI.View')))) return false;
			if (subview.canClickThrough) return false;
			if (!subview.superview) return;

			Object.defineProperty(subview, 'originalSuperview', {
				value: subview.superview,
				configurable: true
			});

			this.endEditingSubview();
			
			var options = {};
			options.superview = subview.superview;
			
			this._isInSubviewEditingMode = true;
			this.editedSubview = subview;
			this.editedSubviewSuperview = options.superview;
			this._onFinishSubviewEditing = options.onFinish;
			this.contentFrameController.editorDidBeginEditingSubview(subview, options);
			
			
			this.manipulator.editedView = subview;

			
			this.registerViewAsDropTarget(subview);
			
			
			
			if (this.viewIsInsideADynamicCell(subview)) {
				var info = this.infoOfCellBasedSuperviewForView(subview);
				info.cellBasedView.editorWillEditPrototypeCell(this, info.cell);
			}

			
			if (this.editedSubview.editorDidBeginExclusiveEditing)
				this.editedSubview.editorDidBeginExclusiveEditing(this);
			
			return true;
};
		
		
Editor.prototype.endEditingSubview = function Editor_endEditingSubview() {
		
			if (this.isInSubviewEditingMode !== true)
				return;
			
			var subview = this.editedSubview;
				
			this._isInSubviewEditingMode = false;

			this.unregisterViewAsDropTarget(subview);
			
			
			this.manipulator.editedView = this._editedView;
			
			this.contentFrameController.editorDidEndEditingSubview();

			if (this._onFinishSubviewEditing)
				this._onFinishSubviewEditing(subview);
			delete this._onFinishSubviewEditing;
			
			
			if (this.viewIsInsideADynamicCell(subview)) {
				var info = this.infoOfCellBasedSuperviewForView(subview);
				info.cellBasedView.editorDidEditPrototypeCell(this, info.cell);
			}
			else if (this.editedSubviewSuperview.editorDidEditSubview)
				this.editedSubviewSuperview.editorDidEditSubview(this, this.editedSubview);
			
			
			if (this.editedSubview.editorDidFinishExclusiveEditing)
				this.editedSubview.editorDidFinishExclusiveEditing(this);

			delete this.editedSubviewSuperview;

			this.editedSubview = this._editedView;
};
		

Editor.prototype.endEditingSubviewAndSelect = function Editor_endEditingSubviewAndSelect() {
			var subview = this.editedSubview;
			var isInsideCell = this.viewIsInsideACell(subview);
			
			if (isInsideCell) this.treeController.unselectAll();

			this.endEditingSubview();
			
			if (!isInsideCell) setTimeout(function () {
				this.selectSingleObject(subview);
			}.bind(this), 10);};
		
		
		Object.defineProperty(Editor.prototype, "isInSubviewEditingMode", {
			get: function () {
				return this._isInSubviewEditingMode === true;
			}});
		
		
		Object.defineProperty(Editor.prototype, "editedSubviewRect", {
			get: function () {
				var rect = {};
				rect.size = this.editedSubview.sizeCopy;
				rect.position = {
					left: this.editedSubview.position.left,
					top: this.editedSubview.position.top +
						this.contentFrameController.contentView.position.top
				};
				if (this.isInSubviewEditingMode) {
					rect.position = this.editedSubview.superview.positionCopy;
				}
				return rect;
			}});
		
	
	
	
Editor.prototype.changeCellPrototypeForItemsView = function Editor_changeCellPrototypeForItemsView(key, newPrototype, itemsView, keepView) {

		newPrototype = JSON.parse(JSON.stringify(newPrototype));

		itemsView[key] = newPrototype;
		delete itemsView._livingCellPrototype;

		itemsView.reloadDataLazy();
};
	
	

	

// role PasteboardResponder (Application) 

Editor.prototype.canCut = function Editor_canCut() {
			return true;};
		
	
Editor.prototype.canCopy = function Editor_canCopy() {
			return this.canCopyItems(this.selection.contents);};
		

Editor.prototype.canPaste = function Editor_canPaste() {
			return !!(this.destinationNodeForPasteOperation);};
		

Editor.prototype.canDuplicate = function Editor_canDuplicate() {
			return this.canCopy();};
		

Editor.prototype.canSelectAll = function Editor_canSelectAll() {
			return this.editedSubview && this.editedSubview.subviews && this.editedSubview.subviews.length;};
		
		
Editor.prototype.canUnselectAll = function Editor_canUnselectAll() {
			return this.treeController && this.treeController.selectedValues.length > 0;};
		

Editor.prototype.canDelete = function Editor_canDelete() {
			return this.canDeleteItems(this.selection.contents);};
		

Editor.prototype.cut = function Editor_cut(e, sender) {
			return this.cutItems(this.selection.items);};
		
	
Editor.prototype.copy = function Editor_copy(e, sender) {
			
			if (document.activeElement.tagName === 'TEXTAREA') return;
			
			return this.copyItems(this.selection.items);};
		
	
Editor.prototype.paste = function Editor_paste(e, sender) {
			return this.pasteInNode(this.destinationNodeForPasteOperation);};
		
	
	
	
	Object.defineProperty(Editor.prototype, "destinationNodeForPasteOperation", {
		get: function () {
			if (!this.editedScene) return;

			var pasteboardCreatesView =
				this.context.pasteboardDelegate.containsType('public.utf8-plain-text') || 
				this.context.pasteboardDelegate.containsType('public.tiff');

			var pasteboardCreatesCellWithUTI = null;
			
			var data;
			if (this.context.pasteboardDelegate.containsType(this.context.objectTreeDataType)) {
				data = this.parsedDataFromPasteboard();
				if (Array.isArray(data)) data = data[0];
				if (!data) return;
				var proto = getPrototype(utiFromData(data));
				if (!proto) return;
				if (isKindOfType(proto, getType('appdoo.iOS.Scene')))
					return;
				if (isKindOfType(proto, getType('Core.UI.View')))
					pasteboardCreatesView = true;
				if (proto.isStaticCell)
					pasteboardCreatesCellWithUTI = proto.UTI;
			}
			
			
			
			if (!pasteboardCreatesView) {

				if (data && this.itemShouldBeFileReference({ UTI: utiFromData(data) })) {
					if (!this.fileReferencesNode) this.addFileReferencesNode();
					return this.fileReferencesNode;
				}
				if (this.selectedItem && this.selectedItem.acceptsMemberWithUTI && this.selectedItem.acceptsMemberWithUTI(utiFromData(data))) {
					return this.selectedItem.node;
				}
				var parentNode = this.selectedItem.node ? this.selectedItem.node.parentNode : null;
				if (parentNode && parentNode.representedObject) {

					if (parentNode.representedObject.acceptsMemberWithUTI && parentNode.representedObject.acceptsMemberWithUTI(utiFromData(data), data)) {
						return parentNode;
					}
					
				}
				if (this.editedScene.objectsNode.representedObject.acceptsMemberWithUTI(utiFromData(data), data))
					return this.editedScene.objectsNode;

				if (this.appObjectsNode.representedObject.acceptsMemberWithUTI(utiFromData(data), data))
					return this.appObjectsNode;
			}
			
			
			if (pasteboardCreatesCellWithUTI) {

				if (this.itemAcceptsMemberWithUTI(this.selectedItem, pasteboardCreatesCellWithUTI))
					return this.selectedItem.node;
					
				if (this.selectedItem.node.parentNode && this.itemAcceptsMemberWithUTI(this.selectedItem.node.parentNode.representedObject, pasteboardCreatesCellWithUTI))
					return this.selectedItem.node.parentNode;
			
				return;	
			}
			
			if (this.editedSubview.encodesSubviews)
				return this.editedSubview.node;
		
		}});
	
	
Editor.prototype.canPasteInItem = function Editor__canPasteInItem(item) {
		return true;};
	
	
Editor.prototype.cutItems = function Editor__cutItems(items) {
		if (this.copyItems(items) === true) {
			this.deleteItems(items);
			return true;
		}};
	
	
Editor.prototype.copyItems = function Editor__copyItems(items) {

		var serializedData = [],
			specialData = [],
			dataType = this.context.objectTreeDataType;
		
		this.context.pasteboardDelegate.clearData();
		
		function worker(item) {
			serializedData.push(item.encodeCloned());
			if (item.specialDataToCopyWithEditor)
				specialData.push(item.specialDataToCopyWithEditor(this));
		}

		if (items[0].superview === this.editedSubview) {

			
			for (var i = 0, c = this.editedSubview.subviews.length; i < c; i++) {
				var subview = this.editedSubview.subviews[i];
				if (items.indexOf(subview) !== -1) worker(subview);
			}
			serializedData.reverse();
			
		}
		else {
			if (Array.isArray(items)) items.every(function (item) {
				worker(item);return true; }, this);
			
		}
		
		var fileURLs = [];
		if (Array.isArray(specialData)) specialData.every(function (dataItem) {

			if (!dataItem) return true;

			for (var pasteboardType in dataItem) {
			
				this.context.pasteboardDelegate.setData(pasteboardType, dataItem[pasteboardType]);
				
				if (pasteboardType === 'public.file-url') {
					fileURLs.push(dataItem[pasteboardType]);
				}
				
			}return true; }, this);
		
		
		if (fileURLs.length > 1) {
			this.context.pasteboardDelegate.setData('NSFilenamesPboardType','<?xml version="1.0" encoding="UTF-8"?>\n\
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">\n\
<plist version="1.0">\n\
<array>\n\
' + fileURLs.map(function(url) { return '	<string>'+url.substr(8)+'</string>'; }).join('\n')+'\n\
</array>\n\
</plist>\n\
');
		}
		
		this.context.pasteboardDelegate.setData(dataType, JSON.stringify(serializedData));
		
		return true;
	};
	
	
Editor.prototype.pasteInNode = function Editor__pasteInNode(node) {

		var editor = this;
		
		this.treeController.beginSelectionChange();
		this.treeController.unselectAll();
	
		if (this.context.pasteboardDelegate.containsType(this.context.objectTreeDataType)) {
			this.pasteObjectTreeInNode(node);
		}

		else if (this.context.pasteboardDelegate.containsType('public.tiff')) {
			this.pasteImageInNode(node);
		}
		
		else if (this.context.pasteboardDelegate.containsType('public.utf8-plain-text')) {
			this.pastePlainText(this.context.pasteboardDelegate.getData('public.utf8-plain-text'));
		}
	
		this.treeController.commitSelectionChange();};
	
	
Editor.prototype.canCopyItems = function Editor__canCopyItems(items) {

		if (!items || !items.length) return false;
		
		var sc = createComponentFromDomain("SelectionController", "appdoo.Editor", this.context, {
			contents: items})
		;
		var parentNodes = sc.getUnique('node.parentNode');
		sc.destroy();
		
		var b1 = !items[0].node,
			b2 = !items[0].node.parentNode,
			b3 = items[0].node.parentNode === this.editedScene.node,
			b4 = items[0].isSection,
			b5 = items[0].node === this.objectsNode,
			b6 = items.indexOf(this.editedScene.navigationBar) !== -1,
			b7 = (this.editedScene.tabBarController && items.indexOf(this.editedScene.tabBarController.tabBar) !== -1);
		
		if (b1 || b2 || b3 || b4 || b5 || b6 || b7) {
		   	return false;
		}
		
		return parentNodes.length === 1;};
	
	
Editor.prototype.canDeleteItems = function Editor__canDeleteItems(items) {
		if (items.length === 0) return false;
		return true;};
	
	
Editor.prototype.prepareDataForInsertion = function Editor__prepareDataForInsertion(data) {
		
		if (this.context.undoManager.isUndoing !== true &&
			this.context.undoManager.isRedoing !== true) {
				this.setNewIDsInClone(data);
		}
};
	

Editor.prototype.insertItemWithDataInNode = function Editor__insertItemWithDataInNode(data, node, setSelected, index) {
	
		this.prepareDataForInsertion(data);

		var item = this.context.projectContext.decodeObjectTree(data);
		
		this.registerInsertedItem(item, setSelected, node, index);
		this.addUndoStepForInsertOperation(item);
		setTimeout(function () {
			if (this.editedScene && this.editedScene.viewController)
				this.context.captureProjectItemImage(this.editedScene.viewController.$id, true);
		}.bind(this), 1);
		this.context.captureProjectItemImage(this.editedScene.viewController.$id);
		return item;
	};
	

Editor.prototype.setNewIDsInClone = function Editor__setNewIDsInClone(clone, mapping) {
		this.context.setNewIDsInClone(clone, mapping);};
	

Editor.prototype.insertElementFromMenu = function Editor__insertElementFromMenu(uti) {
		return this.insertFromBlueprint(uti);};
	
	
Editor.prototype.addUndoStepForInsertOperation = function Editor_addUndoStepForInsertOperation(item) {

		if (!item) return;

		this.context.undoManager.registerChange(this, {
			type: 'insert',
			itemID: item.identify()
		});
	};
	
	
Editor.prototype.parsedDataFromPasteboard = function Editor__parsedDataFromPasteboard() {

		var data;
		
		try {
			data = JSON.parse(this.context.pasteboardDelegate.getData(this.context.objectTreeDataType));
		} catch (err) {
			console.error(err);
		}
		
		return data;
	};
	
	
Editor.prototype.pasteObjectTreeInNode = function Editor__pasteObjectTreeInNode(node) {

		var data = this.parsedDataFromPasteboard();
		
		if (!data) {
			alert(LocalizedString('An error has occured while inserting.'));
			return false;
		}

		var item = node.representedObject;
		
		if (!this.itemAcceptsMembersFromData(item, data)) {
			index = node.inverseIndex;
			node = node.parentNode;
			if (!node) return;
			item = node.representedObject;
		}

		if (!this.itemAcceptsMembersFromData(item, data)) {
			this.context.nativeProxy.sendMessage('beep');
			return;
		}

		var index;

		if (Array.isArray(data)) {
		
			this.treeController.beginSelectionChange();
			this.treeController.unselectAll();
			index = node.childNodes.length;
			for (var i = data.length-1; i >= 0; i--) {
				var item = this.insertItemWithDataInNode(data[i], node, false, index);
				this.treeController.selectValue(item);
				index ++;
			}
			this.treeController.commitSelectionChange(this);
			
		}
		else {
			index = -1;
			var item = this.insertItemWithDataInNode(data, node, true, node.childeNodes.length);
		}

		if (!node.parentNode) this.editedScene.checkSpecialNodes();
};
	
	
Editor.prototype.itemAcceptsMembersFromData = function Editor__itemAcceptsMembersFromData(item, data) {
		if (Array.isArray(data)) {
			var allPass = true;
			data.every(function (dataItem) {
				if (this.itemAcceptsMemberWithUTI(item, utiFromData(dataItem), dataItem))
					return true;
				else allPass = false;
			}.bind(this));
			return allPass;
		}
		else {
			return this.itemAcceptsMemberWithUTI(item, utiFromData(data));
		}};
	

Editor.prototype.pasteImageInNode = function Editor__pasteImageInNode(node) {
		var view = node.representedObject;

		var imageID = this.context.nativeProxy.sendMessage('savePasteboardImageAsFile');

		if (!imageID) {
			console.warn('Importing the pasteboard image failed.');
			return;
		}
		
		this.context.whenImageIsReady(this.context.pathForImageWithID(imageID), function (img) {
		
			this.context.projectContext.registerImageWithID(imageID);

			var imageRef = createComponentFromDomain('ImageReference', 'appdoo', this.context.projectContext, {
				imageID: imageID
			});
	
			var size = { width: img.width/2, height: img.height/2 },
				imageView = createComponentFromDomain('UIImageView', "appdoo.iOS",
				this.context.projectContext,
				{
					size: size,
					position: this.positionForInsertion(size),
					imageRef: imageRef,
					contentMode: "center"
				});
			
			this.registerInsertedItem(imageView, true);
			this.addUndoStepForInsertOperation(imageView);
		
		}.bind(this));
};
	
	
	function countCharacterInString(ch, str) {
		return str.split(ch).length - 1;
	}
	
Editor.prototype.pasteSomethingSpecialFromText = function Editor__pasteSomethingSpecialFromText(text, position) {
		
		if (!text) return;
		
		text = text.trim();
		
		
		if (text[0] === '{' && text[text.length-1] === '}' ||
			text[0] === '[' && text[text.length-1] === ']') {
			
			var isValidJSON;
			try {
				var data = JSON.parse(text);
				isValidJSON = true;
			} catch (err) {
				isValidJSON = false;
			} finally {
				if (isValidJSON) {
					
					var ds = this.insertFromBlueprint('info.appdoo-mac.JSONDataSource');
					ds.location = 'local';
					ds.localJSONData = text;
										
					return true;
				}
			}

		}

		function hasPrefix(str, prefix) {
			return str.substr(0,prefix.length) === prefix;
		}
	
		function hasSuffix(str, suffix) {
			return str.substr(str.length-suffix.length) === suffix;
		}
		
		
		var nOpeningXMLBrackets = countCharacterInString('<', text);
		var nClosingXMLBrackets = countCharacterInString('>', text);
		if (nOpeningXMLBrackets > 0 && nOpeningXMLBrackets===nClosingXMLBrackets && text[0] !== '{' && text[0] !== '[') {
			var htmlView = this.insertFromBlueprint('info.appdoo-mac.SimpleHTMLView', this.editedSubview.node);
			htmlView.content = text;
			return true;
		}
		
		
		if (hasPrefix(text,'http') && (
			hasSuffix(text,'.jpg') || hasSuffix(text,'.gif') || hasSuffix(text,'.png'))) {
			var imageView = this.insertFromBlueprint('appdoo.iOS.UIImageViewWithURL', this.editedSubview.node);
			
			imageView.imageURLString = text;
			return true;
		}
		};
	
	
Editor.prototype.pastePlainText = function Editor__pastePlainText(text, position) {
	
		if (this.pasteSomethingSpecialFromText(text, position))
			return;
	
		var width = 170, height = 22;
		if (text.length > 50) {
			width = 250;
			height = 250;
		}
	
		if (!position) {
			position = this.positionForInsertion({ width: 150, height: 22 });
		}
		else {
			position.left -= width/2;
			position.top -= height/2;
		}
		

		var label = getPrototype('appdoo.iOS.UILabel').createForSuperview(this.editedView);
		label.size = { width: width, height: height };
		label.position = position;
		label.text = text;

		this.registerInsertedItem(label, true);
		this.addUndoStepForInsertOperation(label);
		
		return label;
};
	
	
	
	

Editor.prototype.selectionIsValidForRearranging = function Editor__selectionIsValidForRearranging() {
		return 	this.selection &&
				this.selection.items.length &&
				this.selection.items[0].superview &&
				this.selection.items.indexOf(this.editedSubview) === -1;};
	
	
Editor.prototype.selectionCanBeSentToFront = function Editor__selectionCanBeSentToFront() {
		return this.selectionCanBeSentForward();};
	

Editor.prototype.selectionCanBeSentToBack = function Editor__selectionCanBeSentToBack() {
		return this.selectionCanBeSentBackward();};
	

Editor.prototype.selectionCanBeSentBackward = function Editor__selectionCanBeSentBackward() {
		
		if (!this.selectionIsValidForRearranging())
			return false;
		
		if (this.selection.items.length > 1)
			return true;
		
		return this.itemsCanBeSentBackward(this.selection.items);
};
	

Editor.prototype.selectionCanBeSentForward = function Editor__selectionCanBeSentForward() {

		if (!this.selectionIsValidForRearranging())
			return false;
		
		if (this.selection.items.length > 1)
			return true;

		return this.itemsCanBeSentForward(this.selection.items);};
	
	
Editor.prototype.itemsCanBeSentForward = function Editor__itemsCanBeSentForward(items) {
	
		if (!items) return false;

		var subviewNode = items[0].node;
		if (!subviewNode) return false;
		var subviewIndex = subviewNode.index;

		if (subviewIndex === 0)
			return false;
				
		return true;
		};
	

Editor.prototype.itemsCanBeSentBackward = function Editor__itemsCanBeSentBackward(items) {

		if (!items) return false;

		var subviewNode = items[0].node;
		if (!subviewNode) return false;
		
		var	subviewIndex = subviewNode.index,
			max = items[0].node.parentNode.childNodes.length-1;

		if (subviewIndex === max)
			return false;
				
		return true;
	};
	
	

Editor.prototype.selectionCanBeGrouped = function Editor__selectionCanBeGrouped() {
		return this.itemsCanBeGrouped(this.selection.items);};
	

Editor.prototype.selectionCanBeUngrouped = function Editor__selectionCanBeUngrouped() {
		return this.itemsCanBeUngrouped(this.selection.items);};
	
	
Editor.prototype.itemsCanBeGrouped = function Editor__itemsCanBeGrouped(items) {
		if (!items || !items.length) return false;
		var sc = createComponentFromDomain("SelectionController", "appdoo.Editor", this.context, {
			contents: items})
		;
		var sv = sc.getUnique('superview');
		return sv.length === 1 && !!sv[0];};
	
	
Editor.prototype.itemsCanBeUngrouped = function Editor__itemsCanBeUngrouped(items) {
		var sc = createComponentFromDomain("SelectionController", "appdoo.Editor", this.context, {
			contents: items})
		;
		return sc.itemsHaveEqualUTI &&
			   sc.items[0].UTI === 'appdoo.iOS.ViewGroup';};
	


Editor.prototype.itemsCanBeLocked = function Editor__itemsCanBeLocked(items) {
		var sc = createComponentFromDomain("SelectionController", "appdoo.Editor", this.context, {
			contents: items})
		;
		return sc.getSingle('locked') !== true;};
	

Editor.prototype.itemsCanBeUnlocked = function Editor__itemsCanBeUnlocked(items) {
		var hasLockedItem = false;
		if (Array.isArray(items)) items.every(function (item) {
			if (item.locked) { hasLockedItem = true; return false; }return true; }, this);
		
		return hasLockedItem;};
	

	
	
	function keyEvent__matchesCode__meta__alt__shift(e, keyCode, metaKey, altKey, shiftKey) {
		return e.keyCode === keyCode && e.metaKey === metaKey && e.altKey === altKey && e.shiftKey === shiftKey;
	}
	
Editor.prototype.rotateSelection = function Editor__rotateSelection(reverse) {
		var selectedItem = this.selection.contents[0];

		if (!selectedItem || !selectedItem.node || selectedItem === this.editedScene || selectedItem === this.editedSubview) {
			if (this.editedSubview.node.firstChild) {
				this.selectSingleObject(reverse ? this.editedSubview.subviews[0] : this.editedSubview.node.firstChild.representedObject);
				return true;
			}
			return false;
		}
		
		if (reverse) {

			if (selectedItem.node.previousSibling)
				this.selectSingleObject(selectedItem.node.previousSibling.representedObject);
			else
				this.selectSingleObject(selectedItem.node.parentNode.lastChild.representedObject);

			return true;

		}
		else {
		
			if (selectedItem.node.nextSibling)
				this.selectSingleObject(selectedItem.node.nextSibling.representedObject);
			else
				this.selectSingleObject(selectedItem.node.parentNode.firstChild.representedObject);

			return true;
		}};
	

Editor.prototype.keydownEventHandler = function Editor__keydownEventHandler(e) {
	
		if (e.metaKey) {
	
			
			
			
			if (keyEvent__matchesCode__meta__alt__shift(e, 70, true, false, false)) { 
				this.searchField.focus();
				this.searchField.selectAll();
				e.preventDefault();
				return;
			}
	
	
			
			if (this.inspector && !(e.altKey || e.shiftKey)) {
				for (var i = 0; i < this.inspector.segments.length; i++) {
					if (e.keyCode == 49+i) { 
						this.inspector.selectedIndex = i;
						e.preventDefault();
						return;
					}
				}
			}


			
			
			
			if (keyEvent__matchesCode__meta__alt__shift(e, 189, true, true, false)) {
				this.changeTextSizeFromSelectionByStep(-1);
				return e.preventDefault();
			}
			
			if (keyEvent__matchesCode__meta__alt__shift(e, 187, true, true, false)) {
				this.changeTextSizeFromSelectionByStep(+1);
				return e.preventDefault();
			}
			
			if (keyEvent__matchesCode__meta__alt__shift(e, 66, true, false, false)) {
				this.toggleSelectedTextBoldness();
				return e.preventDefault();
			}
			
			if (keyEvent__matchesCode__meta__alt__shift(e, 73, true, false, false)) {
				this.toggleSelectedTextItalicness();
				return e.preventDefault();
			}
			

			if (this.context.isDebugging) {
			
				
				if (keyEvent__matchesCode__meta__alt__shift(e, 69, true, true, true)) { 
					var uti = prompt('Insert element:','');
					if (uti) {
						if (uti.indexOf('.') === -1) {
							['info.appdoo-mac','appdoo.iOS','appdoo','Core.UI'].every(function (domain) {
								if (getTypeFromDomain(uti,domain)) {
									uti = domain+'.'+uti;
									return false;
								}return true; }, this);
							
						}
						this.insertFromBlueprint(uti, this.editedView.node);
					}
					
					e.preventDefault();
					return;
				}
				
			}
		}

		
		if (e.target.tagName === 'INPUT' ||
			e.target.tagName === 'TEXTAREA') return;


		
		if (keyEvent__matchesCode__meta__alt__shift(e, 39, true, false, false)) {
			this.contentFrameController.rotate();
			return e.preventDefault();
		}

		
		if (keyEvent__matchesCode__meta__alt__shift(e, 37, true, true, false)) {
			if (this.goBack())
				e.preventDefault();
			return;
		}

		
		if (keyEvent__matchesCode__meta__alt__shift(e, 39, true, true, false)) {
			if (this.goForward())
				e.preventDefault();
			return;
		}

		
		if (e.keyCode === 9 && e.altKey && e.target === document.body) {
			if (this.rotateSelection(e.shiftKey))
				e.preventDefault();
			return;
		}
			
		if (this.context.isCancelEvent(e)) {
		
			if (this.isInSubviewEditingMode) {
				this.endEditingSubviewAndSelect();
				e.preventDefault();
				return;
			}

			return;
		}
		
		
		
		if (e.keyCode === 32 && e.altKey === false && e.metaKey === false) {
		
			if (this.goToOverview()) {
				e.preventDefault();
				e.stopPropagation();
			}

			return;
		}
		
		
		if (e.keyCode === 13 && e.metaKey === false) {
		
			if (this.selectionEditDefault(e) === true)
				e.preventDefault();

			else if (this.isInSubviewEditingMode) {
				this.endEditingSubviewAndSelect();
				e.preventDefault();
			}

			return;
		}

		
		if (e.keyCode === 13 && e.metaKey === true && e.altKey === true) {

			if (this.selection.items.length === 1 && typeof this.selection.items[0].action === 'function') {
				this.selection.items[0].action();
				e.preventDefault();
			}

			return;
		}
};
	
	
Editor.prototype.showManipulator = function Editor_showManipulator() {
		if (this.manipulator) this.manipulator.show();};
	

Editor.prototype.hideManipulator = function Editor_hideManipulator() {
		if (this.manipulator) this.manipulator.hide();};
	
	
Editor.prototype.swipeEventHandler = function Editor__swipeEventHandler(e) {
		if (e.detail === 1) {
			this.goBack();
		}
		if (e.detail === 2) {
			this.goForward();
		}};
	
	
Editor.prototype.magnifyEventHandler = function Editor__magnifyEventHandler(e) {
		var magnifyDelta = e.detail/1000000;
		this.contentFrameController.contentScale += magnifyDelta;};
	

	var rotation = 0, rotationBlocked = false;
Editor.prototype.rotationEventHandler = function Editor__rotationEventHandler(e) {

		var rotationDelta = e.detail/1000000;
		rotation += rotationDelta;
		
		if (rotationBlocked) return;
		
		if (Math.abs(rotationDelta) > 1) {
			rotationBlocked = true;
			this.contentFrameController.rotate();
		}
};
	

Editor.prototype.endGestureEventHandler = function Editor__endGestureEventHandler(e) {
		rotationBlocked = false;};
	
	
Editor.prototype.didBecomeMainEventHandler = function Editor__didBecomeMainEventHandler(e) {};
	

Editor.prototype.didResignMainEventHandler = function Editor__didResignMainEventHandler(e) {};
	

Editor.prototype.addWindowEvents = function Editor__addWindowEvents() {
	
		if (this.hasWindowEvents) return;
		this.hasWindowEvents = true;
	
		this._keydownEventHandlerBound = this.keydownEventHandler.bind(this);
		window.addEventListener('keydown', this._keydownEventHandlerBound);

		this._swipeEventHandlerBound = this.swipeEventHandler.bind(this);
		window.addEventListener('swipe', this._swipeEventHandlerBound);

		this._magnifyEventHandlerBound = this.magnifyEventHandler.bind(this);
		window.addEventListener('magnify', this._magnifyEventHandlerBound);

		this._rotationEventHandlerBound = this.rotationEventHandler.bind(this);
		window.addEventListener('rotate', this._rotationEventHandlerBound);

		this._endGestureEventHandlerBound = this.endGestureEventHandler.bind(this);
		window.addEventListener('endGesture', this._endGestureEventHandlerBound);
};
	

Editor.prototype.removeWindowEvents = function Editor__removeWindowEvents() {

		if (!this.hasWindowEvents) return;
		this.hasWindowEvents = false;

		window.removeEventListener('keydown', this._keydownEventHandlerBound);
		window.removeEventListener('swipe', this._swipeEventHandlerBound);
		window.removeEventListener('magnify', this._magnifyEventHandlerBound);
		window.removeEventListener('rotate', this._rotateEventHandlerBound);
		window.removeEventListener('endGesture', this._endGestureEventHandlerBound);
};
	


	

Editor.prototype.handleDrop = function Editor__handleDrop(e, view) {
	
		this.contentFrameController.focus();
	
		var dataTransfer = e.dataTransfer;
	
		if (dataTransfer.types.indexOf(this.context.objectTreeDataType) !== -1) {
			return this.handleComponentDataDrop(e, view);
		}

		if (dataTransfer.types.indexOf(this.context.objectBlueprintDataType) !== -1) {
			return this.handleBlueprintDrop(e, view);
		}
		
		if (dataTransfer.files.length) {
			return this.dropFilesAtItemWithEventCompletion(dataTransfer.files, view, e, function completion (results) {
				this.selectSingleObject(results[results.length-1]);
			}.bind(this));
		}

		if (dataTransfer.types.indexOf('public.tiff') !== -1) {
			return this.handleTIFFDataDrop(e, view);
		}

		if (dataTransfer.types.indexOf('public.utf8-plain-text') !== -1) {
			return this.handlePlainTextDrop(e, view);
		}

		if (dataTransfer.types.indexOf(this.context.resourceReferenceDataType) !== -1) {
			return this.handleResourceReferenceDrop(e, view);
		}

		if (dataTransfer.types.indexOf(this.context.promisedRealObjectsDataType) !== -1) {
			return this.handlePromisedObjectsDrop(e, view);
		}
		
		 console.warn('unhandled drop: ', dataTransfer, dataTransfer.types);
		};
	
	
	function updateGuidelineControllerWithEventInView(editor, guidelineController, e, view) {

		if (!guidelineController) return;

		var coordinatesInView = editor.viewCoordinatesForMouseXY(view, e);
		
		var rX = e.x-(e.dragItem.position.left),
			rY = e.y-(e.dragItem.position.top);
		
		coordinatesInView.x -= rX;
		coordinatesInView.y -= rY;
		
		guidelineController.clear();
		guidelineController.guidePositionForSize(coordinatesInView, e.dragItem.size);

		e.suggestedCoordinates = coordinatesInView;

		var mouseCoordinates = editor.mouseCoordinatesForCoordinatesInView({
				x: coordinatesInView.x + e.dragItem.size.width/2,
				y: coordinatesInView.y + e.dragItem.size.height/2
			}, view);

		mouseCoordinates.x -= e.dragItem.size.width/2;
		mouseCoordinates.y -= e.dragItem.size.height/2;
		
		e.dragItem.position = {
			left: mouseCoordinates.x,
			top: mouseCoordinates.y
		};
		
	}

Editor.prototype.registerViewAsDropTarget = function Editor__registerViewAsDropTarget(view) {
	
		if (view.dropHandler) return;
		
		var editor = this,
			contentScale,
			guidelineController = null,
			draggedBlueprintData,
			draggedItemIsView;
	
		view.dropHandler = {
		
			didEnterWithEvent: function (e) {
				draggedBlueprintData = null;
				draggedBlueprintItemIsView = false;

				if (e.dataTransfer.types &&
					e.dataTransfer.types.indexOf(this.context.objectTreeDataType) !== -1) {
				
					if (e.dragItem) {
	
						contentScale = editor.contentFrameController.contentScale;
						if (contentScale !== 1) {
							e.dragItem.setScaleAnimated(contentScale, true);
						}
						
						guidelineController = editor.manipulator.guidelineController;
						guidelineController.beginShowingGuidelines(true);
						
					}
				
				}

				if (e.dataTransfer.types &&
					e.dataTransfer.types.indexOf(this.context.objectBlueprintDataType) !== -1) {
					
					draggedBlueprintData = JSON.parse(e.dataTransfer.getData(_context.objectBlueprintDataType));
					draggedBlueprintItemIsView = isKindOfType(getPrototype(utiFromData(draggedBlueprintData)), getType('Core.UI.View'));
				}

			}.bind(this),

			didLeaveWithEvent: function (e) {

				if (e.dragItem) {
					var contentScale = editor.contentFrameController.contentScale;
					if (contentScale !== 1) {
						e.dragItem.setScaleAnimated(1, true);
					}
					
					editor.unhighlightView(view);
					
				}
				if (guidelineController) {
					guidelineController.endShowingGuidelines();
					guidelineController = null;
				}
			
			},
			
			dropEffectForEvent: function (e) {
			
				if (!e.dataTransfer.types)
					return 'none';

				if (e.dataTransfer.types.indexOf(this.context.objectTreeDataType) !== -1 ||
					e.dataTransfer.types.indexOf(this.context.objectBlueprintDataType) !== -1) {

				
					if (e.dragItem) {
						
						if (draggedBlueprintData) {
							var data = draggedBlueprintData;
							
							if (!draggedBlueprintItemIsView) {
								this.highlightView(editor.editedSubview);
								return 'move';
							}

							if (!editor.objectIsAllowedToHaveMembersOfUTI(editor.editedSubview, data.UTI)) return 'none';
							
							this.highlightView(editor.editedSubview);
						}

						updateGuidelineControllerWithEventInView(editor, guidelineController, e, view);
					}
				
					return 'move';
				}
				
				
				if (e.dataTransfer.types.indexOf('public.file-url') !== -1) {
					return 'copy';
				}

				if (e.dataTransfer.types.indexOf('public.tiff') !== -1) {
					return 'copy';
				}

				if (e.dataTransfer.types.indexOf('public.utf8-plain-text') !== -1) {
					return 'copy';
				}
				
				if (e.dataTransfer.types.indexOf(this.context.resourceReferenceDataType) !== -1) {
					return 'alias';
				}
				
				return 'none';
				
			}.bind(this),
		
			didDropWithEvent: function (e) {
				if (editor.isPerformingDropOnItemView) return;
			
				editor.unhighlightView(view);
				editor.unhighlightView(_context.editor.contentFrameController.contentView);
			
				if (guidelineController) {
					guidelineController.endShowingGuidelines();
					guidelineController = null;
				}

				var result = editor.handleDrop(e, view);
				if (result) e.preventDefault();
				return result;
			}
		
		};

		this.addDefaultContextMenuToView(view);};
	
	
Editor.prototype.contextMenuForView = function Editor__contextMenuForView(view, isFramingView) {

		var menuData = {
			"$type": "Menu",
			"$domain": "Core.UI",
			"items": [
			  {
				"$type": "MenuItem",
				"$domain": "Core.UI",
				"title": LocalizedString("Paste"),
				"target": this,
				"targetMethod": "paste",
			  },
			  {
				"$type": "MenuItem",
				"$domain": "Core.UI",
				"title": LocalizedString("Select All"),
				"target": this,
				"targetMethod": "selectAll"
			  },
			  {
				"$type" : "MenuItem",
				"$domain" : "Core.UI",
				"separator" : true
			  },
			  {
				"$type": "MenuItem",
				"$domain": "Core.UI",
				"title": LocalizedString("Zoom In"),
				"target": this.contentFrameController,
				"targetMethod": "zoomIn",
			  },
			  {
				"$type": "MenuItem",
				"$domain": "Core.UI",
				"title": LocalizedString("Zoom Out"),
				"target": this.contentFrameController,
				"targetMethod": "zoomOut",
			  },
			]
		};
        






























		
		return this.context.decodeObjectTree(menuData);
};
	
	
Editor.prototype.addDefaultContextMenuToView = function Editor_addDefaultContextMenuToView(view, isFramingView) {
		view.contextMenu = this.contextMenuForView(view, isFramingView);
		view.contextMenu.delegate = this;};
	
	
Editor.prototype.menuNeedsUpdate = function Editor_menuNeedsUpdate(menu) {

		menu.menuItemByTargetMethod('selectAll').enabled = this.canSelectAll();
		menu.menuItemByTargetMethod('paste').enabled = this.canPaste();
		menu.menuItemByTargetMethod('zoomIn').enabled = this.contentFrameController.canZoomIn();
		menu.menuItemByTargetMethod('zoomOut').enabled = this.contentFrameController.canZoomOut();
		
		if (menu.menuItemByTargetMethod('toggleBackgroundStyle')) {
			var miDark = menu.menuItemByTargetMethod('toggleBackgroundStyleDark');
			var miBright = menu.menuItemByTargetMethod('toggleBackgroundStyle');
			miBright.state = !this.contentFrameController.hasDarkBackground;
			miBright.enabled = !!this.contentFrameController.hasDarkBackground;
			miDark.state = !miBright.state;
			miDark.enabled = !miBright.enabled;
		}};
	
	
Editor.prototype.unregisterViewAsDropTarget = function Editor__unregisterViewAsDropTarget(view) {
		view.dropHandler = null;
		view.contextMenu = null;};
	

	
Editor.prototype.highlightView = function Editor__highlightView(view) {

		if (view.isHighlighted) return;
		
		Object.defineProperty(view, 'isHighlighted', {value:true,writable:true});
		this.manipulator.guidelineController.beginShowingGuidelines(true);
		var ctx = this.manipulator.guidelineController.guidelineCanvas.getContext('2d');
		var w = view.size.width, h = view.size.height,
			x = -view.getRelativeX(0, this.editedView.superview),
			y = -view.getRelativeY(0, this.editedView.superview);
			
		var scale = this.contentFrameController._contentScale;
		w *= scale, h *= scale, x *= scale, y*= scale;

		ctx.lineWidth = 1;
		ctx.strokeStyle = 'rgba(0, 121, 255, .5)';
    	if (ctx.setLineDash) ctx.setLineDash([]);

		var gradient = ctx.createLinearGradient(0,0,h,h);
		gradient.addColorStop(0, 'rgba(139, 210, 255, 0.25)');
		gradient.addColorStop(1, 'rgba(0, 121, 255, 0.25)');
		ctx.fillStyle = gradient;
		
		
		
		(function roundRect(ctx, x, y, width, height, radius, fill, stroke) {
		
			if (typeof stroke == "undefined") {
				stroke = true;
			}
			if (typeof radius === "undefined") {
				radius = 5;
			}
			ctx.beginPath();
			ctx.moveTo(x + radius, y);
			ctx.lineTo(x + width - radius, y);
			ctx.quadraticCurveTo(x + width, y, x + width, y + radius);
			ctx.lineTo(x + width, y + height - radius);
			ctx.quadraticCurveTo(x + width, y + height, x + width - radius, y + height);
			ctx.lineTo(x + radius, y + height);
			ctx.quadraticCurveTo(x, y + height, x, y + height - radius);
			ctx.lineTo(x, y + radius);
			ctx.quadraticCurveTo(x, y, x + radius, y);
			ctx.closePath();
			if (stroke) {
				ctx.stroke();
			}
			if (fill) {
				ctx.fill();
			}
			
		})(ctx, x+1,y+1,w-2,h-2, 7*scale, true, true);
		};
	

Editor.prototype.unhighlightView = function Editor__unhighlightView(view) {
		if (!view.isHighlighted) return;
		view.isHighlighted = false;
		this.manipulator.guidelineController.endShowingGuidelines();};
	
	
Editor.prototype.viewCoordinatesForMouseXY = function Editor__viewCoordinatesForMouseXY(view, xyPosition) {

		var contentWrapper = this.contentFrameController.contentWrapper,
			contentScale = this.contentFrameController.contentScale,
			pos = {
				x: contentWrapper.getRelativeX(xyPosition.x) + view.getRelativeX(0, contentWrapper) * contentScale,
				y: contentWrapper.getRelativeY(xyPosition.y) + view.getRelativeY(0, contentWrapper) * contentScale
			};
		
		pos.x /= contentScale;
		pos.y /= contentScale;

		return pos;};
	
	
Editor.prototype.mouseCoordinatesForCoordinatesInView = function Editor__mouseCoordinatesForCoordinatesInView(xyPosition, view) {
	
		var contentWrapper = this.contentFrameController.contentWrapper,
			contentScale = this.contentFrameController.contentScale,
			pos = {
				x: xyPosition.x,
				y: xyPosition.y
			};
		
		pos.x *= contentScale;
		pos.y *= contentScale;

		pos.x -= contentWrapper.getRelativeX(0) + view.getRelativeX(0, contentWrapper) * contentScale;
		pos.y -= contentWrapper.getRelativeY(0) + view.getRelativeY(0, contentWrapper) * contentScale;

		return pos;
};
	


	
	
Editor.prototype.importDataSourceDataFromFile = function Editor__importDataSourceDataFromFile(file, dataSourceUTI, completion) {

		if (!file.path) file.path = this.context.nativeProxy.sendMessage('pathForDraggedFileWithName', file.name);
		
		function finishWithString(string) {

			var ds = getPrototype(dataSourceUTI).createForContext(this.context.projectContext);
			ds.location = 'local';
			ds.name = this.filenameFromPath(file.path);
			this.registerInsertedItem(ds);
			
			ds.localData = string;
			
			if (ds.itemArray &&
				this.validateInsertion('appdoo.iOS.UITableView') !== false &&
				!this.isPerformingDropOnItemView) {
				tableView = getPrototype('appdoo.iOS.UITableView').createForSuperview(this.editedSubview);
				tableView.usesDataSource = true;
				setTimeout(function () {
					tableView.e_dataSourceID = ds.identify();
				}, 0);
				this.registerInsertedItem(tableView, true);
				

				if (completion) completion([ds, tableView]);
				else {
					this.addUndoStepForInsertOperation(ds);
					this.addUndoStepForInsertOperation(tableView);
				}
			}
			
			else {
				this.selectSingleObject(ds);
				if (completion) completion(ds);
				else this.addUndoStepForInsertOperation(ds);
			}
			
		}
		
		this.importTextFileWithCollback(file, finishWithString);};
	
	
Editor.prototype.importTextFileWithCollback = function Editor__importTextFileWithCollback(file, finishWithString) {
	
		if (file.path) {
			finishWithString.call(this, this.context.nativeProxy.sendMessage('stringFromFile', file.path));
		} else {
			var reader = new FileReader();
			reader.onload = function(e) {
				finishWithString.call(this, e.target.result);
			}.bind(this);
	
			reader.readAsText(file);
		}
	};
	
	
Editor.prototype.importPlainTextFromFile = function Editor__importPlainTextFromFile(file, completion, view, index) {

		if (!view) {
			return this.importBinaryFile(file, completion, undefined, undefined, 'text/plain');
		}

		function finishWithString(string) {
			var label = this.pastePlainText(string, null);
			completion(label);
		}
		this.importTextFileWithCollback(file, finishWithString);
	};
	

Editor.prototype.importHTMLFromFile = function Editor__importHTMLFromFile(file, completion, view, index) {

		if (view) {

			function finishWithString(string) {
				var htmlView = this.insertFromBlueprint('info.appdoo-mac.SimpleHTMLView', this.editedSubview.node);
				htmlView.content = string;
				htmlView.margin = 15;
				completion(htmlView);
			}
		
			this.importTextFileWithCollback(file, finishWithString);
		}
		else {
			return this.importBinaryFile(file, completion, undefined, undefined, 'text/html');
		}
};
	

	
	

Editor.prototype.importImage = function Editor__importImage(path) {

		var imageID = this.context.nativeProxy.sendMessage('importImageFromPath', path);

		if (!imageID) {
			alert(LocalizedString('The image could not be read.'));
			return;
		}
		
		this.context.whenImageIsReady(this.context.pathForImageWithID(imageID), function (img) {

			this.context.projectContext.registerImageWithID(imageID);

			var position = this.positionForInsertion({ width: 40, height: 40 }),
				name = this.filenameFromPath(path, true),
				scalar = name.indexOf('@2x') === -1 ? 1 : 2,
				size = { width: img.width/scalar, height: img.height/scalar };
	
			var imageView = createComponentFromDomain('UIImageView', "appdoo.iOS",
				this.context.projectContext,
				{
					size: size,
					position: position,
					imageID: imageID,
					contentMode: "center",
				});
			
			this.registerInsertedItem(imageView, true);

		}.bind(this));
		};
	
	
	
	
Editor.prototype.importImageFileToViewWithOptions = function Editor__importImageFileToViewWithOptions(file, view, options, completion, index) {
	
		if (!file.path) file.path = this.context.nativeProxy.sendMessage('pathForDraggedFileWithName', file.name);

		var contentType = file.type;

		if (file.path) {

			var resourceID = this.context.nativeProxy.sendMessage('importBinaryFileFromPath', file.path),
				name = this.filenameFromPath(file.path, true);

			this.finishImportingImageWithID(resourceID, name, view, contentType, options, completion, index, file.path);

		}
		else {

			
			var reader = new FileReader();
			reader.onload = function(e) {
	
				var imageID = this.context.nativeProxy.sendMessage('importImageFromData', e.target.result, contentType),
					name = this.filenameFromPath(file.name, true);
					
	
				this.finishImportingImageWithID(imageID, name, view, contentType, options, completion, index, file.path);
	
			}.bind(this);
			reader.readAsBinaryString(file);
		}
		};
	
	
Editor.prototype.finishImportingImageWithID = function Editor__finishImportingImageWithID(imageID, name, view, contentType, options, completion, index, originalFilePath) {

		if (!imageID) {
			alert(LocalizedString('The image could not be read.'));
			return;
		}
	
		
		this.context.whenImageIsReady(this.context.pathForImageWithID(imageID), function (img) {

			var shouldSync = _context.shouldSyncFile(name, originalFilePath);
			if (shouldSync === 2) return; 
	
			this.context.projectContext.registerImageWithID(imageID);
			
			if (view && view.DOMNode) {
				var scalar = name && name.indexOf('@2x') === -1 ? 1 : 2;
				var size = { width: img.width/scalar, height: img.height/scalar },
					position = options.position || this.positionForInsertion({ width: 40, height: 40 });
				
				if (options.position) {
					position.left -= (size.width/2)|0;
					position.top -= (size.height/2)|0;
				}
				
				var imageRef = createComponentFromDomain('ImageReference', 'appdoo', this.context.projectContext, {
					imageID: imageID,
					contentType: contentType,
					originalFileInfo: this.context.getFileInfoFromAbsultePath(originalFilePath)
				});
		
				var imageView = createComponentFromDomain('UIImageView', "appdoo.iOS",
					this.context.projectContext,
					{
						size: size,
						position: position,
						contentMode: "center",
						imageRef: imageRef
					});
				
				this.registerInsertedItem(imageView, true);

				if (shouldSync === true) {
					var ref = this.addResourceReference(imageRef.imageID, name, contentType, undefined, originalFilePath);
					imageRef.fileReferenceID = ref.identify();
					imageView.localImageObjectID = ref.identify();
					imageView.sourceType = 'local';
					imageView.imageRef = null;
					imageView.isReferenced = true;
					if (completion) completion([imageView, ref]);
					else {
						this.addUndoStepForInsertOperation(imageView);
						this.addUndoStepForInsertOperation(ref);
					}
				}
				else {
					if (completion) completion(imageView);
					else this.addUndoStepForInsertOperation(imageView);
				}
			}
			else {
				var rr = this.addResourceReference(imageID, name, contentType, index, originalFilePath);
				if (completion) completion(rr);
				else this.addUndoStepForInsertOperation(rr);
			}
	
		}.bind(this));	};
	
	
	
	
	
Editor.prototype.importBinaryFile = function Editor__importBinaryFile(file, completion, view, index, contentType) {

		if (!file.path) file.path = this.context.nativeProxy.sendMessage('pathForDraggedFileWithName', file.name);
	
		if (file.path) {
			var fileID = this.context.nativeProxy.sendMessage('importBinaryFileFromPath', file.path),
				name = this.filenameFromPath(file.path, true);
			this.finishImportingBinaryFileWithID(fileID, name, contentType||file.type, completion, view, index, file.path);
		}
		else {
		
			
			var reader = new FileReader();
			reader.onload = function(e) {
	
				var fileID = this.context.nativeProxy.sendMessage('importBinaryFileFromData', e.target.result, file.type),
					name = this.filenameFromPath(file.name, true);
					
				this.finishImportingBinaryFileWithID(fileID, name, contentType||file.type, completion, view, index, file.path);
	
			}.bind(this);
			reader.readAsBinaryString(file);
		}
};
	
	
Editor.prototype.finishImportingBinaryFileWithID = function Editor__finishImportingBinaryFileWithID(fileID, name, contentType, completion, view, index, originalFilePath) {

		this.context.projectContext.registerItem('resource', fileID);
		var rr = this.addResourceReference(fileID, name, contentType, index, originalFilePath);

		if (view && view.DOMNode && rr.canCreateContainerViewForSuperview(this.editedSubview)) {
			
			var view = rr.createContainerViewForSuperview(this.editedSubview);
			
			this.registerInsertedItem(view);
			
			if (completion) completion([rr,view]);
			else {
				this.selectSingleObject(view);
				this.addUndoStepForInsertOperation(rr);
				this.addUndoStepForInsertOperation(view);
			}
		}
		else {
			if (completion) completion(rr);
			else {
				this.selectSingleObject(rr);
				this.addUndoStepForInsertOperation(rr);
			}
		}};
	
	
Editor.prototype.importHeaderFile = function Editor__importHeaderFile(file, completion) {
	
		return this.importBinaryFile(file, completion, undefined, undefined, 'text/x-h');
		};
	

Editor.prototype.importFontFromFile = function Editor__importFontFromFile(file, completion, extension) {
	
		var mime;
		if (extension === 'otf') mime = 'application/x-font-opentype';
		if (extension === 'ttf') mime = 'application/x-font-ttf';
		
		return this.importBinaryFile(file, completion, undefined, undefined, mime);};
	
	
	
	var userFonts = [];
Editor.prototype.loadFont = function Editor_loadFont(fontFile) {
		if (userFonts.indexOf(fontFile) !== -1) return;
		userFonts.push(fontFile);
		this.updateLoadedFonts();};
	

Editor.prototype.unloadFont = function Editor_unloadFont(fontFile) {
		var i = userFonts.indexOf(fontFile); if (i === -1) return;
		userFonts.splice(i, 1);
		this.updateLoadedFonts();};
	
	
	var fontTimer, fontStyleContainer;
Editor.prototype.updateLoadedFonts = function Editor_updateLoadedFonts() {
		if (fontTimer) clearTimeout(fontTimer);

		fontTimer = setTimeout(function () {
			console.trace();
			if (!fontStyleContainer) {
				fontStyleContainer = document.createElement('style');
				fontStyleContainer.type = 'text/css';
				fontStyleContainer.id = 'user-fonts';
				document.getElementsByTagName('head')[0].appendChild(fontStyleContainer);
			}
			var str = '', i = 0;
			if (Array.isArray(userFonts)) userFonts.every(function (font) {
				str += '@font-face { font-family: "'+font.fontInfo.name+'";';
				str += ' src: url("'+(font.filePath||'').replace(/\"/g,'\"')+'")';
				if (font.contentType === 'application/x-font-opentype') {
					str += ' format("opentype")';
				}
				else {
					str += ' format("truetype")';
				}
				str += ';';
				str += '}'
				i++;return true; }, this);
			

			fontStyleContainer.innerHTML = str;

			this.inspector.resetFontCache();
			fontTimer = null;
		}.bind(this), 100);};
	

Editor.prototype.deviceChanged = function Editor_deviceChanged(popupButton) {
		this.deviceIdentifierChanged(popupButton.value);};
	
	
Editor.prototype.deviceIdentifierChanged = function Editor_deviceIdentifierChanged(identifier) {
		this.context.changeSimulatedDevice(identifier);

		if (this.editedScene.e_showsNavigationBar) {
			this.editedScene.navigationBar.unselectForEditor(this);
		}
		this.contentFrameController.updateTabBar();
		this.context.updateAllPreviewImages(this.editedScene.viewController.$id);
		this.saveItem();};
	

Editor.prototype.addResourceReference = function Editor_addResourceReference(resourceID, name, contentType, index, originalFilePath) {
		var ref = this.context.addResourceReference(resourceID, name, contentType, index, originalFilePath);
		this.registerInsertedItem(ref, false, this.fileReferencesNode, index);
		return ref;};
	
	
Editor.prototype.prettifyFilename = function Editor__prettifyFilename(name) {

		function isNumber(x) {
			return typeof x === 'number';
		}

		var pos;
		
		
		pos = name.indexOf('.');
		if (pos !== -1) {
			name = name.substr(0, pos);
		}
		
		
		pos = name.lastIndexOf('@2x');
		if (pos === name.length-3) {
			name = name.substr(0, name.length-3);
		}
		
		
		var result = '', chBefore;
		for (var i = 0, c = name.length; i < c; i++) {
			var ch = name.charAt(i);
			if (ch.toUpperCase() === ch && !(!isNumber(ch*1) && !isNumber(chBefore*1)) && ch !== ' ' && chBefore !== ' ') {
				result += ' ';
			}
			if (ch === '_') {
				ch = ' ';
			}
			if (!(ch === ' ' && chBefore === ' '))
				result += ch;
			chBefore = ch;
		}
		result = result.trim();
		
		return result;};
	
	
Editor.prototype.filenameFromPath = function Editor_filenameFromPath(path) {
		return this.context.nativeProxy.sendMessage('filenameForPath', path);};
	
	

	
	
// role ManipulatorDelegate 
		
Editor.prototype.manipulatorWillMoveItems = function Editor_manipulatorWillMoveItems(manipulator, items) {};
		
	
Editor.prototype.manipulatorDidMoveItems = function Editor_manipulatorDidMoveItems(manipulator, items) {};
		
		
Editor.prototype.manipulatorIsMovingItems = function Editor_manipulatorIsMovingItems(manipulator, items) {};
		
		
Editor.prototype.editedViewsForManipulator = function Editor_editedViewsForManipulator(editedView) {
			var subviews = [];
			var editedViewNode = editedView.node;
			if (!editedViewNode) { console.log('this.editedView has no node property: ', this.editedView);  return; }
			this.addSubviewsForManipulator(editedViewNode, subviews);
			return subviews;};
		
	
	
	
Editor.prototype.addSubviewsForManipulator = function Editor__addSubviewsForManipulator(viewNode, result) {

		if (Array.isArray(viewNode.childNodes)) viewNode.childNodes.every(function (childNode) {
			if (childNode.representedObject.superview) {
				var canClickThrough = childNode.representedObject.canClickThrough;
				if (!canClickThrough)
					result.push(childNode.representedObject);
				else {
					this.addSubviewsForManipulator(childNode, result);
				}
			}return true; }, this);
		
	};
	
	
// role SegmentedViewControllerDelegate (Core.UI) 
	
Editor.prototype.segmentedViewControllerDidLoadViewAtIndex = function Editor_segmentedViewControllerDidLoadViewAtIndex(svc, index) {};
		
	
	
	

// role ContentFrameControllerDelegate 
		
Editor.prototype.contentFrameDidChangeContentScale = function Editor_contentFrameDidChangeContentScale(scale) {
			if (this.manipulator !== undefined)
				this.manipulator.contentScale = scale;
			if (!this.context.isOffscreen)
				this.context.nativeProxy.sendMessage('contentScaleDidChange',scale);};
		
	
	
	
	


	
	
// role DataContextStackController 

Editor.prototype.dataContextForDataSource = function Editor_dataContextForDataSource(dataSource, enumerableItemAccess) {
		
			if (!this.dataContextsController) return;
		
			return this.dataContextsController.valuePassingTest(function (x) {
				return x.dataSource === dataSource && !(enumerableItemAccess && !x.indexPath);
			});
			};
		

Editor.prototype.pushDataContextForDataSource = function Editor_pushDataContextForDataSource(dataSource) {
		
			var dataContext = this.dataContextForDataSource(dataSource, false);
			if (dataContext) {
				this.updateDataContext(dataContext);
				return dataContext;
			}
					
			if (!dataSource.providesRootData) return;
		
			dataContext = createComponentFromDomain("DataContext", "appdoo", this.context, {
				dataSource: dataSource,})
			;
			
			this.pushDataContext(dataContext);
			return dataContext;
			};
		

Editor.prototype.pushDataContextForDataSourceItem = function Editor_pushDataContextForDataSourceItem(dataSource, indexPath) {
		
			if (!dataSource) return;
			if (!indexPath) indexPath = { section: 0, item: 0 };

			var dataContext = createComponentFromDomain("DataContext", "appdoo", this.context, {
				dataSource: dataSource,
				indexPath: indexPath})
			;

			this.pushDataContext(dataContext);
			
			return dataContext;
		};
		

Editor.prototype.pushDataContextForDataContextWithDataKeyPath = function Editor_pushDataContextForDataContextWithDataKeyPath(dataContext, keyPath) {

			if (!keyPath) return;
			if (!dataContext) return;
			
			dataContext.keyPath = keyPath;
			this.updateDataContext(dataContext);
		};
		

Editor.prototype.pushDataContext = function Editor_pushDataContext(dataContext) {
			if (!this.dataContextsController) return;
			this.dataContextsController.addValue(dataContext);};
		
		
Editor.prototype.removeDataContextForDataSource = function Editor_removeDataContextForDataSource(dataSource) {
			var dataContext = this.dataContextForDataSource(dataSource);
			if (dataContext) {
				this.dataContextsController.removeValue(dataContext);
				dataContext.destroy();
			}};
		

Editor.prototype.popDataContextForDataSourceItem = function Editor_popDataContextForDataSourceItem(dataSource, indexPath) {
		
			if (Array.isArray(this.dataContextsController.contents)) this.dataContextsController.contents.every(function (ctx) {
				if (ctx.dataSource === dataSource && ctx.indexPath === indexPath) {
					this.dataContextsController.removeValue(ctx);
					ctx.destroy();
					return false;
				}return true; }, this);
			
		};
		
		
Editor.prototype.updateDataContext = function Editor_updateDataContext(dataContext) {

			this.context.broadcastValueChangeForKeyPathInObject(this.dataContextsController.contents.indexOf(dataContext), this.dataContextsController, this);
		};
		

		
		
		
		Object.defineProperty(Editor.prototype, "bindableProperties", {
			get: function () {
				var items = [['null.null','']];
				if (Array.isArray(this.dataContexts)) this.dataContexts.every(function (dataContext) {
					if (dataContext.allowsBindings === false) return true;
					if (!dataContext.dataSource) return true;
					var ds = dataContext.dataSource,
						dsChildrenId = ds.identify()+'[]',
						keys = Object.keys(dataContext.dataItemController.contents);
					if (Array.isArray(keys)) keys.every(function (key) {
						items.push([dsChildrenId+'.'+key, ds.nameForKey(key)]);return true; }, this);
					return true; }, this);
				
				if (items.length === 1) return [];
				return items;
			}});
		

		Object.defineProperty(Editor.prototype, "bindableObjects", {
			get: function () {
				var r = [
					['',LocalizedString('(No Selection)')]
				];

				if (Array.isArray(this.dataContexts)) this.dataContexts.every(function (ctx) {
					if (!ctx.allowsBindings) return true;

					var displayedName = ctx.dataSource.readableValue;
					r.push([ctx.name, displayedName]);return true; }, this);
				
				
				return r;
			}});
		

Editor.prototype.bestKeyPathGuessForBinding = function Editor_bestKeyPathGuessForBinding(binding, keyPathBefore) {
		
			if (!binding.dataController) return;
			
			var availableKeyPaths = binding.dataController.getAvailableKeyPathsForCurrentDestination().map(function (item) { if (item[0])return item[0]; });
			
			if (availableKeyPaths[0] === '^NULL^') availableKeyPaths.shift();

			keyPathBefore = keyPathBefore || binding.destinationKeyPath;
			if (keyPathBefore && availableKeyPaths.indexOf(keyPathBefore) !== -1)
				return keyPathBefore;

			if (binding.sourceKeyPath === 'title') {
				if (availableKeyPaths.indexOf('title') !== -1) return 'title';
				if (availableKeyPaths.indexOf('contents.title') !== -1) return 'contents.title';
			}

			var keyPathsInUse = [];
			
			(function checkView(view) {
				if (Array.isArray(view.bindings)) view.bindings.every(function (_binding) {
					
					if (_binding.destination === binding.destination) {
						keyPathsInUse.push(_binding.destinationKeyPath);
					}return true; }, this);
				
				if (Array.isArray(view.subviews)) view.subviews.every(function (subview) {
					checkView(subview);return true; }, this);
				
			})(this.editedView);

			var diff = (function diffArray(b, a) {
			
				return b.filter(function(i) {
					return !(a.indexOf(i) > -1);
				});
				
			})(availableKeyPaths, keyPathsInUse);

			return diff[0] || availableKeyPaths[0];};
		
	
	


	

// role FileDropHandler 
		
		
		
Editor.prototype.dropFilesAtItemWithEventCompletion = function Editor_dropFilesAtItemWithEventCompletion(files, view, e, completion, index) {

			var numberOfFiles = files.length;
			var numberOfProcessedFiles = 0;
			var results = [];
			var self = this;
			var didCallCompletionHandler = false;
			var onFileComplete = function (obj) {
			
				if (Array.isArray(obj)) {
					if (Array.isArray(obj)) obj.every(function (v) {
						results.push(v);return true; }, this);
					
				}
				else if (obj) results.push(obj);
				
				numberOfProcessedFiles++;
				if (numberOfProcessedFiles === numberOfFiles) {
					onAllComplete();
				}
				
			};
			var onAllComplete = function () {
				didCallCompletionHandler = true;
				if (Array.isArray(results)) results.every(function (v) {
					self.addUndoStepForInsertOperation(v);return true; }, this);
				
				if (completion) {
					completion(results);
					didCallCompletionHandler = true;
				}
				self = null;
			};

			
			
			if (completion) setTimeout(function () {
				if (didCallCompletionHandler) return;
				completion(results);
			}.bind(this), 5000*10);

			if (e) e.preventDefault();
			var didFail;
		
			for (var i = 0; i < numberOfFiles; i++) {
				var file = files[i];

				var extension = getPathExtension(file.path||file.name);
				if (extension === 'h') {
					this.importHeaderFile(file, onFileComplete);
					continue;
				}
			
				if (_context.supportedImageMimeTypes.indexOf(file.type) !== -1) {
					var options = {};
					if (e && view && view.DOMNode) {
						var scale = this.contentFrameController._contentScale;
						options.position = this.positionOfMouseInView(e, view);
						this.importImageFileToViewWithOptions(file, view, options, onFileComplete, index);
					} else {
						this.importBinaryFile(file, onFileComplete, view, index);
					}
				}

				else if (['audio/x-m4a', 'audio/mp4', 'audio/mpeg', 'video/x-m4v', 'video/mp4', 'application/pdf'].indexOf(file.type) !== -1) {
					this.importBinaryFile(file, onFileComplete, view, index);
				}

				else if (file.type === 'text/csv') {
					this.importDataSourceDataFromFile(file, 'info.appdoo-mac.CSVDataSource', onFileComplete);
				}

				else if (file.type === 'application/json') {
					this.importDataSourceDataFromFile(file, 'info.appdoo-mac.JSONDataSource', onFileComplete);
				}

				else if (file.type === 'application/rss+xml') {
					this.importDataSourceDataFromFile(file, 'info.appdoo-mac.RSS2DataSource', onFileComplete);
				}

				else if (file.type === 'text/javascript') {
					this.importDataSourceDataFromFile(file, 'info.appdoo-mac.JavaScriptContainer', onFileComplete);
				}
				
				else if (file.type === 'text/plain') {
					
					this.importPlainTextFromFile(file, onFileComplete, view, index);
				}

				else if (file.type === 'text/html' || file.type === 'application/xhtml+xml') {
					this.importHTMLFromFile(file, onFileComplete, view, index);
				}
				else  if (_context.supportedOfficeMimeTypes.indexOf(file.type) !== -1) {
					this.importBinaryFile(file, onFileComplete, view, index);
				}
				else  if (extension === 'pages' || extension === 'numbers' || extension === 'keynote' || extension === 'key') {
					this.importBinaryFile(file, onFileComplete, view, index);
				}

				else {
					
					
					
					if (extension === 'atom') {
						this.importDataSourceDataFromFile(file, 'info.appdoo-mac.AtomDataSource', onFileComplete);
						continue;
					}

					if (extension === 'otf' || extension === 'ttf') {
						this.importFontFromFile(file, onFileComplete, extension);
						continue;
					}
					
					alertd('Unsupported file type:', file.type);
				
					didFail = true;
					
					this.context.showIncompatibilityErrorForFile(file, (files.length > 1))
				}
				
			}

			return didFail ? false : true;
};
		
	
	
	
Editor.prototype.dumpDataTransfer = function Editor__dumpDataTransfer(e) {

		if (Array.isArray(e.dataTransfer.types)) e.dataTransfer.types.every(function (type) {
			var data = e.dataTransfer.getData(type);
			 console.log(type+':', data, typeof data);return true; }, this);
		
};
	
	
Editor.prototype.handleComponentDataDrop = function Editor__handleComponentDataDrop(e, view) {
	
		var dataTransfer = e.dataTransfer,
			data = dataTransfer.getData(this.context.objectTreeDataType),
			controlData = JSON.parse(data),
			options = controlData,
			id = controlData.$type,
			domain = controlData.$domain;

		if (!controlData) {
			console.warn('The drop operation did fail.');
			 console.log(data);
			console.trace();
			return;
		}
		
		if (this.validateInsertion(utiFromData(controlData)) === false) {
			console.warn('The drop operation is invalid.');
			return false;
		}
		
		var contentFrame = this.contentFrameController.view,
			contentWrapper = this.contentFrameController.contentWrapper;
		
		if (e.suggestedCoordinates) {
			options.frame.origin = {
				x: e.suggestedCoordinates.x|0,
				y: e.suggestedCoordinates.y|0
			};
		}

		var component = createComponentFromDomain(id, domain, this.context.projectContext, options);
		var subview = component.view ? component.view : component;
		if (!e.suggestedCoordinates) {
			subview.position = this.positionForInsertion(subview.size);
		}
		
		this.registerInsertedItem(subview, true);
		this.addUndoStepForInsertOperation(subview);
		
		return true;
	};
	
	
Editor.prototype.handleBlueprintDrop = function Editor__handleBlueprintDrop(e, view) {

		var dataTransfer = e.dataTransfer,
			dataJSON = dataTransfer.getData(this.context.objectBlueprintDataType),
			data = JSON.parse(dataJSON);

		if (this.handleSpecialBlueprintDrop(data.UTI)) return;

		var isView = isKindOfType(getPrototype(data.UTI), getType('Core.UI.View'));

		var parentNode = view.node;
		if (!isView) {
			parentNode = this.preferredObjectNodeForItemWithUTI(data.UTI, data.properties);
		}

		var item = this.insertFromBlueprint(data.UTI, parentNode, isView, view);
		
		if (item && data.properties) {
			for (var key in data.properties) {
				item[key] = data.properties[key];
			}
		}
		
		if (item && item.DOMNode && typeof e.x === 'number') {
		
			var p = this.positionOfMouseInView(e, view, item);

			var scale = this.contentFrameController._contentScale;
			if (item.size.width < view.size.width) {
				item.position.left = p.left;
			}
			if (item.size.height < view.size.height) {
				item.position.top = p.top;
			}

		}
		
		this.animateInsertion(item);

		return item;
};
	
	
Editor.prototype.animateInsertion = function Editor__animateInsertion(item) {

		if (!item || !item.style) return;

		item.style({ opacity: 0 });
		
		setTimeout(function () {
			item.beginAnimations();
			item.style({ opacity: 1, webkitTransform: '' });
			item.commitAnimations();
		});
		};
	
	
Editor.prototype.selectSingleObject_withDelay_ = function Editor__selectSingleObject_withDelay_(obj, delay) {
		setTimeout(function () {
			this.selectSingleObject(obj);
		}.bind(this), delay || 0);};
	

Editor.prototype.selectSingleObject = function Editor__selectSingleObject(obj) {
		this.treeController.beginSelectionChange();
		this.treeController.unselectAll();
		this.treeController.selectValue(obj);
		this.treeController.commitSelectionChange();};
	
	
Editor.prototype.handleSpecialBlueprintDrop = function Editor__handleSpecialBlueprintDrop(UTI) {
		
		if (UTI === 'appdoo.iOS.UINavigationBar') {
			this.editedScene.e_showsNavigationBar = true;
			this.selectSingleObject(this.editedScene.navigationBar);
			return true;
		}

		if (UTI === 'appdoo.iOS.UITabBarItem') {
			this.editedScene.e_showsInTabBar = true;
			this.selectSingleObject_withDelay_(this.editedScene.viewController.tabBarItem, 0);
			return true;
		}
			};
	
	
Editor.prototype.positionOfMouseInView = function Editor__positionOfMouseInView(e, view, obj) {
	
		var p = this.viewCoordinatesForMouseXY(view, e);
		p = { left: p.x, top: p.y };
			
		if (obj) {
			p.left -= obj.size.width/2;
			p.top -= obj.size.height/2;
		}
		
		return p;
};
	
	
Editor.prototype.handleTIFFDataDrop = function Editor__handleTIFFDataDrop(e, view) {

		var path = e.dataTransfer.getData('public.utf8-plain-text'),
			imageID = this.context.nativeProxy.sendMessage('importImageFromDragPasteboard');
		
		this.finishImportingImageWithID(imageID, this.filenameFromPath(path), view, 'image/tiff', {
			position: this.positionOfMouseInView(e, view)
		});
		
		return true;};
	

Editor.prototype.handlePlainTextDrop = function Editor__handlePlainTextDrop(e, view) {
		var text = e.dataTransfer.getData('public.utf8-plain-text');
		var label = this.pastePlainText(text, this.positionOfMouseInView(e, view));
		return true;};
	
	
Editor.prototype.handleResourceReferenceDrop = function Editor__handleResourceReferenceDrop(e, view) {

		var ids = e.dataTransfer.getData(this.context.resourceReferenceDataType).split(',');
		
		this.treeController.beginSelectionChange();
		this.treeController.unselectAll();
		
		if (Array.isArray(ids)) ids.every(function (id) {
			var rr = this.context.projectContext.globals[id];
			if (!rr) return true;
			var obj = rr.createContainerViewForSuperview(view);
			if (!obj) return true;
			obj.position = this.positionOfMouseInView(e, view, obj);
			this.registerInsertedItem(obj);
			this.addUndoStepForInsertOperation(obj);
			this.treeController.selectValue(obj);return true; }, this);
		
		
		this.treeController.commitSelectionChange();
		
		return true;};
	
	
Editor.prototype.handlePromisedObjectsDrop = function Editor__handlePromisedObjectsDrop(e, view) {

		var ids = e.dataTransfer.getData(this.context.promisedRealObjectsDataType).split(','),
			objs = [];
		
		if (Array.isArray(ids)) ids.every(function (id) {
			var rr = this.context.projectContext.globals[id];
			objs.push(rr);return true; }, this);
		
		
		if (objs.length === 1) return objs[0];
		
		return objs;
	};
	
	
	
	
	
Editor.prototype.checkImplications = function Editor__checkImplications(eventType, item, keyPath) {

		if (this.isOpening) return;

		if (!item || !item.node) {
			return;
		}
		
		
		if (item.isStaticCell
			&& keyPath && keyPath.indexOf('size.') === 0
			&& item !== this.editedSubview) {
			
			if (this.updateCellViewTimer)
				clearTimeout(this.updateCellViewTimer);

			this.updateCellViewTimer = setTimeout(function () {
				
				
				if (item.cellView) item.cellView.size = item.sizeCopy;
				cellBasedView.arrangeSubviews();
				cellBasedView.contentSizeDidChange();
				if (cellBasedView.drawBackground)		cellBasedView.drawBackground();
				
				
				
				this.manipulator.updateSizeModifierButtons();
			}.bind(this), 1);
		}

		
		
		
		var info = this.infoOfCellBasedSuperviewForView(item);

		var cellBasedView = info.cellBasedView,
			cell = info.cell;
		
		if (!cellBasedView) return;
		if (!cellBasedView.isDynamicCell || !cellBasedView.isDynamicCell(cell)) return;
		
		
		
		if (this.updateCellViewTimer) clearTimeout(this.updateCellViewTimer);
		this.updateCellViewTimer = setTimeout(function () {
			cellBasedView.updatePrototypesForEditor(this);
			delete this.updateCellViewTimer;
		}.bind(this), 1);};
	

Editor.prototype.objectIsAllowedToHaveMembersOfUTI = function Editor_objectIsAllowedToHaveMembersOfUTI(view, uti, data) {
		return this.itemAcceptsMemberWithUTI(view, uti, data);};
	
	
Editor.prototype.infoOfCellBasedSuperviewForView = function Editor__infoOfCellBasedSuperviewForView(view) {

		var node = view.node, cellBasedView, cell;
		
		while (node) {
			if (!node.parentNode) break;
			if (!node.parentNode.representedObject.encodesSubviews) {
				cellBasedView = node.parentNode.representedObject;
				if (cellBasedView.isStaticSection)
					cellBasedView = cellBasedView.itemsView;
				cell = node.representedObject;
				break;
			}
			node = node.parentNode;
		}
		if (cellBasedView === this.editedScene) return {};
		
		return { cellBasedView: cellBasedView, cell: cell };
	};
	
	
Editor.prototype.viewIsInsideADynamicCell = function Editor__viewIsInsideADynamicCell(view) {
		
		var info = this.infoOfCellBasedSuperviewForView(view);
		if (info.cellBasedView) {
			if (info.cellBasedView.cellPrototypeView === info.cell) return true;
		}
		return false;
};
	

Editor.prototype.viewIsInsideACell = function Editor__viewIsInsideACell(view) {
		
		var info = this.infoOfCellBasedSuperviewForView(view);
		if (info.cellBasedView) return true;
		return false;
};
	
	
	
	
	
// role Observer (Core) 

Editor.prototype.observedObjectSelectionDidChange = function Editor_observedObjectSelectionDidChange(obj, sender) {
		
			var selectedValues = obj.selectedValues;

			
			
			this.selection.items = selectedValues.length ?
				selectedValues : (this.isInSubviewEditingMode ? [this.editedSubview] : [this.editedScene]);
			
			if (this.manipulator.dragRect ||
				this.manipulator.isPerformingViewChange) return;

			var superviews = this.selection.getUnique('node.parentNode.representedObject');
			
			
			if (this.isInSubviewEditingMode && selectedValues.length === 1
				&& selectedValues[0] === this.editedSubview)
					return;
					
			if (superviews.length > 1 ||
				superviews[0] === this.editedView ||
				!superviews[0] ||
			   (selectedValues.length > 1 && selectedValues[0].isStaticCell)) {
			   
				this.endEditingSubview();
				
			}
			else if (superviews[0] && superviews[0] !== this.editedView) {
				
				if (superviews[0].encodesSubviews)
					this.beginEditingSubview(superviews[0]);
					
				else if (selectedValues[0] && selectedValues[0].encodesSubviews) 
					this.beginEditingSubview(selectedValues[0]);
			}
};
		

Editor.prototype.observedObjectValueDidDisappearForKey = function Editor_observedObjectValueDidDisappearForKey(obj, item, key, sender) {

			if (obj === this.context.projectInstancesController) {
			
				
				if(this.editedViewController && key === this.editedViewController.$id)
					this.closeItem(true);

			}
			
			else if (obj === this.treeController) {
				this.checkImplications('disappear', item.representedObject);
				this.unregisterItem(item.representedObject, sender);

			}
};
		

Editor.prototype.observedObjectValueWillDisappearForKey = function Editor_observedObjectValueWillDisappearForKey(obj, item, key, sender) {

			if (item.parentNode && item.parentNode.representedObject.removeMember) {
				item.parentNode.representedObject.removeMember(item.representedObject);
			}
		};
		
		
Editor.prototype.observedObjectValueDidAppearForKey = function Editor_observedObjectValueDidAppearForKey(obj, key, sender) {

			if (!this.editedSubview) return;
			if (this.isPerformingGroupingOperation) return;

			var item = obj.get(key),
				isView = isKindOfType(item, getType('Core.UI.View'));
			
			if (!item || !item.node || item.node.parentNode === this.editedScene.node) return;

			if (isView) this.checkImplications('appear', item);
			
			this.registerItem(item, item.node);
			
			if (item.isStaticCell) {
				var newSection = item.node.parentNode.representedObject;
				if (item === this.editedSubview) this.endEditingSubview();
				if (item.section) item.section.removeCell(item);
				newSection.addCell(item, item.node.index);
				return;
			}

			if (item.node.parentNode) {
				
				if (item.node.parentNode && item.node.parentNode.representedObject.addMember) {
					var index = key.split('.').pop()*1;
					item.node.parentNode.representedObject.addMember(item, index);
				}

				if (isView) {

					
					
					
					var superview = item.node.parentNode.representedObject;
	
					if (superview.encodesSubviews) {
					
						
						
						var shouldRecalculatePosition = item.superview !== undefined && !this.viewIsInsideACell(item.superview) && !this.viewIsInsideACell(superview);

						if (shouldRecalculatePosition) {
						
							var deltaX, deltaY;

							var container = this.contentFrameController.containerView;
							var dx1 = superview.getRelativeX(0, container);
							var dx2 = item.superview.getRelativeX(0, container);
							var dy1 = superview.getRelativeY(0, container);
							var dy2 = item.superview.getRelativeY(0, container);
							deltaX = dx1-dx2;
							deltaY = dy1-dy2;
							
							if (deltaX) item.position.left += deltaX;
							if (deltaY) item.position.top += deltaY;
						}
				
						
						var index = superview.subviews.length - item.node.index;

						superview.insertSubviewAtIndex(item, index);
					
					}

				}
			} else {
				if (isView) this.editedSubview.addSubview(item);
			}
			
			if (isView) {
				if (item.superview === this.editedSubview)
					this.manipulator.register(item);
				else
					this.manipulator.unregister(item);
			}
};
		

		var imageReferenceType = getType('appdoo.ImageReference');

Editor.prototype.observedObjectValueWillChangeForKeyPath = function Editor_observedObjectValueWillChangeForKeyPath(obj, keyPath, sender) {
			var value = obj.get(keyPath);

			if (isKindOfType(value, imageReferenceType)) {
				this.context.projectContext.unregisterImageWithID(value.imageID);
			}};
		

Editor.prototype.observedObjectValueDidChangeForKeyPath = function Editor_observedObjectValueDidChangeForKeyPath(obj, keyPath, sender) {

			this.checkImplications('change', obj.contents, keyPath);
			
			var value = obj.get(keyPath);

			if (isKindOfType(value, imageReferenceType)) {
				this.context.projectContext.registerImageWithID(value.imageID);
			}
			
			if ((keyPath.indexOf('position.') === 0 ||
				keyPath.indexOf('size.') === 0) &&
				obj.contents.superview &&
				sender !== obj.contents.superview.layoutResolver) {
				
				this.context.prototypeDevicesBar.publishChange({ object: obj.contents, keyPath: 'frame', valueNow: obj.frame });

				this.updateLayoutForView(obj.contents.superview);
			}

			if (keyPath.indexOf('bindings.') === 0) {
				var components = keyPath.split('.');
				var lastPathComponent = components[components.length-1];
				
				if (lastPathComponent.indexOf('destination') === 0) {
					if (lastPathComponent === 'destination') {

						var binding = obj.get('bindings.'+components[1]);
				
						if (binding && !(binding.destinationObject && binding.destinationObject.$id === binding.destination)) {
					
							var destinationObject = this.context.projectContext.connectableObjects[binding.destination];
							
							Object.defineProperty(binding, 'destinationObject', {
								enumerable: false,
								value: destinationObject,
								configurable: true
							});
						}
					}
					obj.contents.applyBindings();
				}
			}

			if (this.editedViewController && obj === this.editedViewController.dataController) {

				
				
				this.context.projectInstancesController.setValueForKeyPath(obj.get(keyPath), this.editedViewController.$id+'.'+keyPath, this);

				
				return;
			}

			if (obj === this.context.projectInstancesController) {
			
				
				
				if (this.editedViewController && keyPath.split('.')[0] === this.editedViewController.$id) {
					
					var value = obj.get(keyPath),
						_keyPath = keyPath.substr(keyPath.indexOf('.')+1);
					
					this.editedViewController.dataController.setValueForKeyPath(value, _keyPath, sender);
						
				}
				
				return;
			}
			
};
		
	
Editor.prototype.observedObjectValueDidChangeKey = function Editor_observedObjectValueDidChangeKey(obj, oldKey, newKey, keyPath, sender) {
		
			if (obj === this.treeController) {
			
				var node = obj.nodeForKeyPath(keyPath).childNodes[newKey];
				var item = node.representedObject;

				if (!item) return;

				
				this.checkImplications('keyChange', item); 
				
				
				if (item.isStaticCell && item.section) {
					item.section.reorderCell(item, oldKey, newKey);
					return;
				}
				
				
				if (item.superview) {
				
					var superview = item.superview,
						newSubviewIndex = superview.subviews.length-1-newKey;
	
					item.removeFromSuperview(true);
					superview.insertSubviewAtIndex(item, newSubviewIndex);
	
				}

				if (node.parentNode && node.parentNode.representedObject && node.parentNode.representedObject.moveMember) {
					node.parentNode.representedObject.moveMember(item, oldKey, newKey);
				}

			}
};
		
	
	
	
Editor.prototype.sendForwardFromContextMenu = function Editor_sendForwardFromContextMenu() {
		return this.arrangeElementFromMenu('sendForward', this.selectionForContextMenu);};
	

Editor.prototype.sendBackwardFromContextMenu = function Editor_sendBackwardFromContextMenu() {
		return this.arrangeElementFromMenu('sendBackward', this.selectionForContextMenu);};
	

// role EditorActionHandler 
	
		
		
Editor.prototype.arrangeElementFromMenu = function Editor_arrangeElementFromMenu(arrangeType, selection) {
		
			if (!selection) selection = this.treeController.selectedValues;
			
			if (arrangeType === 'sendToFront') {
				if (Array.isArray(selection)) selection.every(function (view) {

					var oldIndex = view.node.index,
						newIndex = 0;

					view.node.parentNode.moveChildNodeFromIndexToIndex(oldIndex, newIndex, this.manipulator);
return true; }, this);
				
			}
			else if (arrangeType === 'sendToBack') {
				if (Array.isArray(selection)) selection.every(function (view) {

					var oldIndex = view.node.index,
						newIndex = view.node.parentNode.childNodes.length-1;
					
					view.node.parentNode.moveChildNodeFromIndexToIndex(oldIndex, newIndex, this.manipulator);return true; }, this);
				
			}
			else if (arrangeType === 'sendForward') {
				if (Array.isArray(selection)) selection.every(function (view) {

					var oldIndex = view.node.index,
						newIndex = oldIndex-1;

					view.node.parentNode.moveChildNodeFromIndexToIndex(oldIndex, newIndex, this.manipulator);return true; }, this);
				
			}
			else if (arrangeType === 'sendBackward') {
				if (Array.isArray(selection)) selection.every(function (view) {

					var oldIndex = view.node.index,
						newIndex = oldIndex+1;

					view.node.parentNode.moveChildNodeFromIndexToIndex(oldIndex, newIndex, this.manipulator);return true; }, this);
				
			}
			else if (arrangeType === 'group') {
				this.groupItems(this.selection.itemsInOriginalOrder);
			}
			else if (arrangeType === 'ungroup') {
				this.ungroupItems(this.selection.contents);
			}
			else if (arrangeType === '20007') {
				this.selection.alignSelectionLeft();
			}
			else if (arrangeType === '20008') {
				this.selection.alignSelectionHorizontally();
			}
			else if (arrangeType === '20009') {
				this.selection.alignSelectionRight();
			}
			else if (arrangeType === '20010') {
				this.selection.alignSelectionTop();
			}
			else if (arrangeType === '20011') {
				this.selection.alignSelectionVertically();
			}
			else if (arrangeType === '20012') {
				this.selection.alignSelectionBottom();
			}
	};
		
		

		
		
Editor.prototype.groupItems = function Editor_groupItems(items, UTI, setSelected, groupID) {
			if (!items) return;
			if (setSelected === undefined) setSelected = true;
			if (!UTI) UTI = 'appdoo.iOS.ViewGroup';
			
			
			items.sort(function (a, b) { return a.node.index > b.node.index ? 1 : -1; });
		
			var sc = createComponentFromDomain("SelectionController", "appdoo.Editor", this.context, {
				contents: items})
			;
			
			var parentNode = items[0].node.parentNode,
				index = items[0].node.index;
			
			var top = Math.min.apply(null, sc.get('position.top')),
				bottom = Math.max.apply(null, sc.get('position.bottom')),
				left = Math.min.apply(null, sc.get('position.left')),
				right = Math.max.apply(null, sc.get('position.right'));
			
			var viewGroup = createComponent(UTI, this.context.projectContext, {
				items: items,
				isExpandedInEditorOutline: true,
				size: { width: right-left, height: bottom-top },
				position: { left: left, top: top },
				autoresizingMask: 36
			});
			if (groupID) viewGroup.$id = groupID;
			this.registerInsertedItem(viewGroup, false, parentNode);
			this.addUndoStepForInsertOperation(viewGroup);
			
			this.isPerformingGroupingOperation = true;

			if (setSelected) this.treeController.beginSelectionChange();
			if (Array.isArray(items)) items.every(function (item) {
				if (setSelected) this.treeController.unselectNode(item.node);
				item.position.left -= left;
				item.position.top -= top;
				this.treeController.moveNodeToNodeAtIndex(item.node, viewGroup.node, -1, this);
				viewGroup.insertSubviewAtIndex(item,0);
				this.manipulator.unregister(item);return true; }, this);
			
			if (setSelected) {
				this.treeController.selectValue(viewGroup);
				this.treeController.commitSelectionChange();
			}

			this.isPerformingGroupingOperation = false;
			
			return viewGroup;
			};
		
		
Editor.prototype.undoGroup = function Editor_undoGroup(change) {};
		

Editor.prototype.ungroupItems = function Editor_ungroupItems(items) {
			if (Array.isArray(items)) items.every(function (item) {
				this.ungroupItem(item);return true; }, this);
			};
		

Editor.prototype.ungroupItem = function Editor_ungroupItem(groupItem) {

			if (!(isKindOfType(groupItem, getType('appdoo.iOS.ViewGroup'))))
				return false;

			this.context.undoManager.disableRegistration();

			if (this.editedSubview === groupItem)
				this.endEditingSubview();

			var groupItemParentNode = groupItem.node.parentNode,
				groupItemIndex = groupItem.node.index,
				groupItemWasSelected = this.treeController.nodeIsSelected(groupItem.node),
				groupItemChildNodes = clone(groupItem.node.childNodes),
				groupItemLeft = groupItem.position.left,
				groupItemTop = groupItem.position.top;
			
			this.isPerformingGroupingOperation = true;
			
			
			if (Array.isArray(groupItemChildNodes)) groupItemChildNodes.every(function (childNode) {
				groupItemParentNode.insertChildNodeAtIndex(childNode, groupItemIndex++);

				var superview = groupItemParentNode.representedObject;
				var view = childNode.representedObject;
				superview.addSubview(view);
				view.position.left += groupItemLeft;
				view.position.top += groupItemTop;
				this.manipulator.register(view);return true; }, this);
			

			
			this.deleteItem(groupItem);
			
			
			if (groupItemWasSelected) {
				this.treeController.beginSelectionChange();
				if (Array.isArray(groupItemChildNodes)) groupItemChildNodes.every(function (childNode) {
					this.treeController.selectNode(childNode);return true; }, this);
				
				this.treeController.commitSelectionChange();
			}

			this.isPerformingGroupingOperation = false;
			this.context.undoManager.enableRegistration();

			this.context.undoManager.registerChange(this, {
				type: this.context.undoManager.isUndoing ? 'ungroupFromUndo' : 'ungroup',
				itemIDs: groupItemChildNodes.map(function (node) { return node.representedObject.identify(); }),
				UTI: groupItem.UTI,
				groupItemID: groupItem.$id
			});
			
			return true;};
		

Editor.prototype.undoUngroup = function Editor_undoUngroup(change) {
			var items = change.itemIDs.map(function (itemID) {
				return this.context.projectContext.globals[itemID];
			}.bind(this));
			this.groupItems(items, change.UTI, false, change.groupItemID);};
		


		
		
		Object.defineProperty(Editor.prototype, "currentZoomIsOriginalSize", {
			get: function () {
				return this.contentFrameController.contentScale === 1.0;
			}});
		

		
	
Editor.prototype.selectAll = function Editor_selectAll() {

			
			if (document.activeElement && document.activeElement.tagName === 'TEXTAREA') {
				document.activeElement.select();
				return;
			}

			this.manipulator.selectAll();};
		

Editor.prototype.unselectAll = function Editor_unselectAll() {
			this.treeController.unselectAll();};
		
		
Editor.prototype.deleteItems = function Editor_deleteItems(items) {
			
			var operationIsValid = true;
			if (Array.isArray(items)) items.every(function (item) {
				if (!this.itemIsDeletable(item)) {
					operationIsValid = false; return false;
				}return true; }, this);
			
			
			if (!operationIsValid) return false;
		
			this.treeController.beginSelectionChange();
			if (Array.isArray(items)) items.every(function (item) {
				this.deleteItem(item, this);return true; }, this);
			
			
			this.treeController.commitSelectionChange(this.manipulator);
			
			this.context.captureProjectItemImage(this.editedScene.viewController.$id);
			if(this.editedScene) {
				this.context.editSceneWithID(this.editedScene.$id)
			}

			return true;};
		
	
Editor.prototype.deleteSelection = function Editor_deleteSelection() {
			var items = clone(this.treeController.selectedValues);
			this.treeController.unselectAll();
			return this.deleteItems(items);};
		
		
Editor.prototype.itemIsDeletable = function Editor_itemIsDeletable(item, node) {
		
			if (!node) node = this.treeController.nodeForRepresentedObject(item);

			if (node === this.viewNode) return false;
			if (node === this.objectsNode) return false;
			if (node === this.navigationObjectsNode) return false;
			if (node === this.appObjectsNode) return false;
			if (node === this.fileReferencesNode) return false;
			
			return true; 
		};
		
		
Editor.prototype.deleteItem = function Editor_deleteItem(item) {

			var node = this.treeController.nodeForRepresentedObject(item);
			if (!node) return;

			if (!this.itemIsDeletable(item, node)) return false;
			if (this.editedSubview === item) this.endEditingSubview();

			if (item.deleteForEditor) {
				if (item.deleteForEditor(this) === false) {
					return false;
				}
			}

			var segue = this.editedScene.segueForView(item);
			if (segue) {
				this.editedScene.removeSegue(segue);
			}

			var changeType = this.context.undoManager.isUndoing ?
				'deleteFromUndo' : 'delete';

			this.context.undoManager.registerChange(this, {
				type: changeType,
				itemData: item.encode(),
				itemIndex: node.inverseIndex,
				parentKeyPath: node.parentNode.keyPath
			});
			
			if (item.node && item.node.parentNode) {
				var parentNode = item.node.parentNode;
				if (parentNode.representedObject.removeChildForEditor) {
					parentNode.representedObject.removeChildForEditor(item, this);
				}
			}

			if (node) node.remove();
			
			if (this.dataContextForDataSource(item)) {
				this.removeDataContextForDataSource(item);
			}

			if (isKindOfType(item, getType('Core.UI.View'))) {
				item.removeFromSuperview();
			}
			else {
				item.destroy();
			}
			return true;
};
		
	
Editor.prototype.duplicateSelection = function Editor_duplicateSelection() {
			if (!this.canCopy()) {
				this.context.nativeProxy.sendMessage('beep');
				return;
			}
			return this.duplicateItems(this.treeController.selectedValues, true);};
		
		

Editor.prototype.duplicateItems = function Editor_duplicateItems(items, selectResult) {

			var serializedData = [];

			items.sort(function (a, b) { return a.node.index > b.node.index ? 1 : -1; });

			if (Array.isArray(items)) items.every(function (item) {
				serializedData.push(item.encodeCloned());return true; }, this);
			

			if (selectResult) {
				this.treeController.beginSelectionChange();
				this.treeController.unselectAll();
			}
			
			var newObjects = [];
			serializedData.reverse();
			
			var i = 0;
			if (Array.isArray(serializedData)) serializedData.every(function (data) {
				var component = this.insertItemWithDataInNode(data, items[i].node.parentNode, false);
				newObjects.push(component);
				i++;return true; }, this);
			
			
			if (selectResult) {
				if (Array.isArray(newObjects)) newObjects.every(function (obj) {
					this.treeController.selectValue(obj);return true; }, this);
				
				
				this.treeController.commitSelectionChange();
			}
			
			return newObjects;};
		
		

		

Editor.prototype.insertFromBlueprint = function Editor_insertFromBlueprint(elementUTI, parentNode, parentIsAView, droppedOnView) {

			var typeConstructor = getType(elementUTI),
				prototype;
			
			if (typeConstructor === undefined) {
				alert(LocalizedString1('Unknown element UTI: "%1"', elementUTI));
				return;
			}
			
			prototype = typeConstructor.prototype;
			

			if (prototype.createForContext === undefined &&
				prototype.createForEditor === undefined &&
				prototype.createForSuperview === undefined) {
				console.warn('Missing createForEditor() or createForSuperview() implementation in', prototype);
				return;
			}

			
			var item;
			if (parentNode && parentNode.representedObject && parentNode.representedObject.position && prototype.createForSuperview) {
				item = prototype.createForSuperview(parentNode.representedObject);
			}
			if (!item) {
				if (prototype.createForContext) {
					item = prototype.createForContext(this.context.projectContext, { droppedOnView: droppedOnView });
				}
				else if (prototype.createForEditor) {
					item = prototype.createForEditor(this, {});
				}
				else return;
			}
			
			if (item === true) {
				return true;
			}

			if (!item) {
				return;
			}
			
			
			if (item.position)
				item.position = this.positionForInsertion(item.size);
			else {
				if (parentNode && parentNode.representedObject.size)
					parentNode = undefined;
			}
			
			this.registerInsertedItem(item, true, parentNode);

			this.addUndoStepForInsertOperation(item);
	
			return item;
};
		
		
Editor.prototype.validateInsertion = function Editor_validateInsertion(elementUTI) {
		
			if (!this.editedScene)
				return false;
		
			var t = getPrototype(elementUTI);
			if (!t) return false;
			
			var itemIsAView = isKindOfType(t, getType('Core.UI.View'));
			if (!itemIsAView) return true;
				
			return this.objectIsAllowedToHaveMembersOfUTI(this.editedSubview, elementUTI);};
		

	
	
	
	
	
	
// role UndoCapableObject (Core) 

Editor.prototype.readableUndoName = function Editor_readableUndoName(change) {

			var undoNameForType = {
				'delete': 			LocalizedString('Delete Item'),
				'insert':			LocalizedString('Insert Item'),
				'group':			LocalizedString('Group'),
				'ungroupFromUndo':	LocalizedString('Group'),
				'ungroup':			LocalizedString('Ungroup'),
				'groupFromUndo':	LocalizedString('Ungroup'),
			};
			
			return undoNameForType[change.type];
};
		

Editor.prototype.readableUndoDetails = function Editor_readableUndoDetails(change) {

			if (change.type === 'delete')
				return change.itemData.type;

			if (change.type === 'insert')
				return change.itemID;
};
		
	
Editor.prototype.undoChange = function Editor_undoChange(change) {

			if (change.type === 'delete')
				return this.undoDelete(change);

			if (change.type === 'deleteFromUndo')
				return this.undoDelete(change);

			if (change.type === 'undoDelete')
				return this.redoDelete(change);

			if (change.type === 'insert')
				return this.undoInsert(change);

			if (change.type === 'group' || change.type === 'groupFromUndo')
				return this.undoGroup(change);

			if (change.type === 'ungroup' || change.type === 'ungroupFromUndo')
				return this.undoUngroup(change);
};
		

	

	
	
Editor.prototype.undoDelete = function Editor__undoDelete(change) {
		
		var data = change.itemData,
			superview,
			item;

		this.prepareDataForInsertion(data);

	
		item = this.context.projectContext.decodeObjectTree(data);

		var parentNode = this.treeController.nodeForKeyPath(change.parentKeyPath);
		if (!parentNode) return;
		
		this.registerInsertedItem(item, false, parentNode, change.itemIndex);
		
		this.context.undoManager.registerChange(this, {
			type: 'undoDelete',
			itemID: item.identify()
		});
		
		
		if (!this.insertedItems) {

			this.insertedItems = [];

			setTimeout(function () {
			
				this.treeController.beginSelectionChange();
				this.treeController.unselectAll();
				if (Array.isArray(this.insertedItems)) this.insertedItems.every(function (item) {
					this.treeController.selectValue(item, this);return true; }, this);
				
				this.treeController.commitSelectionChange();
				delete this.insertedItems;
				
			}.bind(this), 1);
		
		}
		this.insertedItems.push(item);
		
	};
	

Editor.prototype.redoDelete = function Editor__redoDelete(change) {
		var item = this.context.projectContext.globals[change.itemID];
		this.deleteItem(item);
		this.context.captureProjectItemImage(this.editedScene.viewController.$id);
		if(this.editedScene) {
			this.context.editSceneWithID(this.editedScene.$id)
		}};
	

Editor.prototype.undoInsert = function Editor__undoInsert(change) {
		var item = this.context.projectContext.globals[change.itemID];
		this.deleteItem(item);
		this.context.captureProjectItemImage(this.editedScene.viewController.$id);
		if(this.editedScene) {
			this.context.editSceneWithID(this.editedScene.$id)
		}};
	
	
Editor.prototype.subviewPath = function Editor__subviewPath(object) {
		var subviewIndex = object.superview.subviews.indexOf(object);
		return 'editor.editedView.subviews.'+subviewIndex;};
	
	
	
Editor.prototype.addEditedSubviewDataToPersistantID = function Editor__addEditedSubviewDataToPersistantID(persistantID, subviewIndex) {
	
		var path = this.subviewPath(this.editedSubviewSuperview);

		persistantID.editedSubviewSuperview = path+'.dataController';
		
		var listView = this.editedSubviewSuperview;
		
		if (this.editedSubview === listView.listHeaderView) {
			persistantID.editedSubviewType = 'listHeader';
			path += '.listHeaderView';
		}
		else if (this.editedSubview === listView.listFooterView) {
			persistantID.editedSubviewType = 'listFooter';
			path += '.listFooterView';
		}
		else {
			persistantID.editedSubviewType = 'cell';
			path += '.cellPrototype';
		}
		
		if (subviewIndex >= 0) {
			path += '.subviews.'+subviewIndex;
		}
		
		persistantID.path = path+'.dataController';
};
	


Editor.prototype.persistantIDForController = function Editor_persistantIDForController(controller) {

		if (controller === this)
			return 'editor';

		if (controller === this.treeController)
			return 'treeController';

		if (this.editedScene &&
			controller === this.editedScene.dataController)
			return 'editedScene.dataController';
		
		if (controller.parentObject) {
			var node = this.treeController.nodeForRepresentedObject(controller.parentObject);
			if (node) {
				return '{"path":"'+node.keyPath+'","controllerKey":"'+controller.controllerKey+'"}';
			}
		}

		};
	

Editor.prototype.controllerForPersistantID = function Editor_controllerForPersistantID(id) {
	
		if (!id) {
			console.warn('Missing id.');
			console.trace();
			return;
		}
	
		var obj;
	
		
		if (id[0] === '{') {
			var info = JSON.parse(id);
			obj = this.treeController.get(info.path);
			return obj ? obj[info.controllerKey] : null;
		}
	
		
		obj = this.context.dissolveKeyPathWithContextObject(id, this);

		return obj;
};
	
	
Editor.prototype.undoManagerWillPerformUndo = function Editor__undoManagerWillPerformUndo(event) {};
	
	
Editor.prototype.undoManagerDidRegisterChange = function Editor__undoManagerDidRegisterChange(event) {
		this.context.prototypeDevicesBar.publishChange(event.detail);};
	
	
	Object.defineProperty(Editor.prototype, "providesBindableData", {
		get: function () {
			return this.dataContextsController.numberOfValues > 1;
		}});
	
	

	
	
	function uppercaseFirst(str) {
		return str.charAt(0).toUpperCase() + str.substr(1);
	}
	
	
	
	
	Object.defineProperty(Editor.prototype, "layoutRelationTargets", {
		get: function () {
			var targets = [['null','']], selectionItems = this.selection.items;
			if (!this.editedSubview) return targets;
			if (Array.isArray(this.editedSubview.subviews)) this.editedSubview.subviews.every(function (subview) {
				if (subview === selectionItems[0]) return true;
				targets.push([subview.identify(), subview.readableValue]);return true; }, this);
			
			return targets;
		}});
	
	
	
	
	
Editor.prototype.goToOverview = function Editor_goToOverview() {
		this.saveItem();
		this.context.captureProjectItemImage(this.editedScene.viewController.$id);
		return this.context.showOverview();};
	
	
	
	

Editor.prototype.listViewDidSelectRowAtIndexPath = function Editor_listViewDidSelectRowAtIndexPath(listView, indexPath) {
		var index = indexPath.item;
		var scene = listView.dataSource.dataForRowAtIndex(index);

		if (this.editedScene.$id === scene.$id) {
			this.editorSourceView.goToOutlineAnimated(true);
		}
		else {
			setTimeout(function () { this.editorSourceView.goToOutlineAnimated(true); }.bind(this), 200);
			this.openItem(scene);
		}};
	
	
	
	
	
Editor.prototype.updateSegueForView__type__destination__ = function Editor_updateSegueForView__type__destination__(view, segueType, newDestinationSceneID) {
	
		if (this.context.isOffscreen) return;

		if (!this.editedScene) return;
		if (!view || (view.node && view.node.parentNode === this.appObjectsNode)) {
			return;
		}

		var segue = this.editedScene.segueForView(view);
		
		if (segue) {
			if (newDestinationSceneID)
				segue.destinationSceneID = newDestinationSceneID;
			else
				this.editedScene.removeSegue(segue);
		} else {
			if (!newDestinationSceneID) return;
			segue = this.editedScene.context.decodeObjectTree({
				$type: 'Segue',
				$domain: 'appdoo.iOS',
				destinationSceneID: newDestinationSceneID,
				viewID: view.$id
			});
			this.editedScene.addSegue(segue);
		}
};
	
	
	
	
	
	Object.defineProperty(Editor.prototype, "inspectorIsVisible", {
		get: function () { return !this.rightSplitView.viewIsCollapsedAtIndex(1); }});
	

	Object.defineProperty(Editor.prototype, "elementListIsVisible", {
		get: function () { return !this.mainSplitView.viewIsCollapsedAtIndex(0); }});
	
	
	Object.defineProperty(Editor.prototype, "newItemsList", {
		get: function () {
			return this.outlineViewContainer.subviews[1].subviews[0];
		}});
	
	
	Object.defineProperty(Editor.prototype, "newItemsListContainer", {
		get: function () {
			return this.newItemsList.superview;
		}});
	

Editor.prototype.getEditorAppearance = function Editor_getEditorAppearance() {
		var data = {};
		
		data.elementListIsVisible = this.elementListIsVisible;
		data.inspectorIsVisible = this.inspectorIsVisible;
		data.simulates35Inch = this.contentFrameController.isSimulating3_5InchDisplay;
		data.inspectorCollapsedGroups = this.inspector.collapsedGroups;
		data.globalObjectsNodeIsExpandedInEditorOutline = this.appObjectsNode.representedObject.isExpandedInEditorOutline;
		data.fileReferencesNodeIsExpandedInEditorOutline = this.fileReferencesNode.representedObject.isExpandedInEditorOutline;

		if (this.newItemListDataSource) {
			data.collapsedNewItemSections = this.newItemListDataSource.collapsedSections;
			if (this.newItemsListContainer)
				data.heightOfNewItemsList = this.newItemsListContainer.size.height|0;
		}
		
		if (this.inspector) {
			data.inspectorCurrentSegment = this.inspector.selectedIndex;
		}

		data.contentScale = this.contentFrameController._contentScale;
        data.editorHasDarkBackground = false; 
		data.historyStack = this.historyManager.stack;
		data.historyStackPosition = this.historyManager.stackPosition;
		
		return data;};
	

Editor.prototype.setEditorAppearance = function Editor_setEditorAppearance(data) {

		if (!data) return;
		if (this.context.isOffscreen) return;
		
		if (!data.elementListIsVisible)
			this.mainSplitView.collapseViewAtIndexAnimated(0, false);
		if (!data.inspectorIsVisible)
			this.rightSplitView.collapseViewAtIndexAnimated(1, false);
		if (data.simulates35Inch) {
			this.contentFrameController.toggle3_5InchDisplay();
		}
		if (data.inspectorCollapsedGroups && this.inspector)
			this.inspector.collapsedGroups = data.inspectorCollapsedGroups;
		if (data.collapsedNewItemSections) {
			if (this.newItemListDataSource) 
				this.newItemListDataSource.collapsedSections = data.collapsedNewItemSections;
		}
		if (data.inspectorCurrentSegment && this.inspector) {
			this.inspector.selectedIndex = data.inspectorCurrentSegment;
		}
		if (data.contentScale) {
			this.contentFrameController._contentScale = data.contentScale;
		}
		if (data.editorHasDarkBackground)
			
		if (data.historyStack) {
			this.historyManager.stack = data.historyStack;
			this.historyManager.stackPosition = data.historyStackPosition;
		}
			

		if (this.newItemsListContainer) {
			var delta;
			if (data.heightOfNewItemsList) {
				delta = data.heightOfNewItemsList-this.newItemsListContainer.size.height;
			} else {
				if (this.context.isEditingNewProject) delta = 50; else delta = 50;
			}
			if (delta > window.innerHeight-this.newItemsListContainer.size.height)
				delta = window.innerHeight-this.newItemsListContainer.size.height - 150;
				
			if (delta && delta > -400) {
				this.outlineViewContainer.subviews[0].size.height -= delta;
				this.newItemsListContainer.size.height += delta;
				this.outlineViewContainer.layoutSubviews();
			}
		}
};
	

Editor.prototype.getOptimalWindowSize = function Editor_getOptimalWindowSize() {
		var size = this.contentFrameController.contentWrapper.sizeCopy;
		
		size.width += 30+100;
		size.height += 20*2+10;
		
		if (this.elementListIsVisible) size.width += this.outlineViewContainer.size.width;
		if (this.inspectorIsVisible) size.width += this.inspector.view.size.width;
		
		if (this.elementListIsVisible || this.inspectorIsVisible) {
			size.height = Math.max(size.height, 540);
		}
		return JSON.stringify(size);};
	
	
Editor.prototype.handleDblClickInOutline = function Editor_handleDblClickInOutline(e, senderLabel) {
		var node = senderLabel.superview.superview.dataset;
		if (!node) return;
		
		if (isKindOfType(node.representedObject, getType('appdoo.ResourceReference'))) {
			node.representedObject.openWithDefaultApplication();
			return;
		}
		
		this.editNameFromOutlineCellLabel(e, senderLabel);};
	
	
Editor.prototype.editNameFromOutlineCellLabel = function Editor__editNameFromOutlineCellLabel(e, senderLabel) {
		var node = senderLabel.superview.superview.dataset;
		if (!node) return;
		if (!node.representedObject.nameIsEditable) return;

		var style = senderLabel.encode().style;
		style.textAlign = 'left';
		delete style.color;
		delete style.textShadow;
		var valueBefore = senderLabel.text;

		var ftf = createComponentFromDomain("FloatingTextField", "Core.UI", this.context, {
    		text: senderLabel.text,
    		size: senderLabel.sizeCopy,
    		position: senderLabel.positionCopy,
    		style: style,
    		maximumWidth: senderLabel.sizeCopy.width,
    		multiLine: false,
    		delegate: {
    			textFieldDidBeginEditing: function (textField) {
    				senderLabel.hidden = true;
    				
    				
    				var p = textField.value.lastIndexOf('@2x.');
    				if (p === -1) p = textField.value.lastIndexOf('.');
    				if (p !== -1 && p >= textField.value.length-9) {
    					setTimeout(function () {
	    					textField.focus();
		    				textField.setSelectionRange(0, p);
		    			}, 1);
	    			}
    			}.bind(this),
    			textFieldDidEndEditing: function (textField) {
    				senderLabel.hidden = false;
    				if (!node.representedObject.dataController) return;
    				
    				var v = textField.value;
    				if (valueBefore === v) return;
    				if ('e_name' in node.representedObject) {
	    				node.representedObject.dataController.setValueForKey(v, 'e_name');
    				}
    				else {
	    				node.representedObject.dataController.setValueForKey(v, 'name');
	    				node.representedObject.readableValueDidChange(v);
	    			}
    				this.refreshInspector();
    			}.bind(this)
    		}})
    	;

		senderLabel.superview.addSubview(ftf);};
	
	

Editor.prototype.updateLayout = function Editor_updateLayout(now) {
		this.updateLayoutForView(this.editedSubview, now);};
	
	
Editor.prototype.updateLayoutForView = function Editor__updateLayoutForView(view, now) {
		if (view && view.layoutResolver) {
			if (now)	view.layoutResolver.updateLayoutNow();
			else		view.layoutResolver.updateLayout();
		}
		else {
			this.shoudUpdateLayout = true;
		}
	};
	
	
	
	

Editor.prototype.contextMenuForItems = function Editor_contextMenuForItems(items) {

		this.selectionForContextMenu = items;

		var defaultMenu = this.contextMenuForSelection(items);
		if (!defaultMenu) return;

		var selectionAreViews = true;
		if (Array.isArray(items)) items.every(function (item) {
			if (!isKindOfType(item, getType('Core.UI.View'))) {
				selectionAreViews = false;
				return false;
			}return true; }, this);
		
		
		var	canCopy = this.canCopyItems(items),
			canPaste = items.length === 1 && this.canPasteInItem(items[0]),
			canDelete = this.canDeleteItems(items),
			canGroup = this.itemsCanBeGrouped(items),
			canUngroup = this.itemsCanBeUngrouped(items),
			canLock = selectionAreViews && this.itemsCanBeLocked(items),
			canUnlock = this.itemsCanBeUnlocked(items);
		
		defaultMenu.menuItemByTargetMethod('editGroupFromContextMenu').hidden = !canUngroup || !selectionAreViews;
		defaultMenu.menuItemByTargetMethod('ungroupFromContextMenu').hidden = !canUngroup || !selectionAreViews;
		defaultMenu.menuItemByTargetMethod('groupFromContextMenu').hidden = !canGroup;

		defaultMenu.menuItemByTag(100001).hidden = (!canUngroup && !canGroup);

		defaultMenu.menuItemByTargetMethod('unlockFromContextMenu').hidden = !canUnlock;
		defaultMenu.menuItemByTargetMethod('lockFromContextMenu').hidden = !canLock;

		defaultMenu.menuItemByTag(100002).hidden = (!canUnlock && !canLock);

		defaultMenu.menuItemByTargetMethod('cutFromContextMenu').hidden = !canCopy; 
		defaultMenu.menuItemByTargetMethod('copyFromContextMenu').hidden = !canCopy; 
		defaultMenu.menuItemByTargetMethod('pasteFromContextMenu').hidden = !canPaste; 
		defaultMenu.menuItemByTargetMethod('deleteFromContextMenu').hidden = !canDelete; 

		return defaultMenu;};
	
	
Editor.prototype.cutFromContextMenu = function Editor_cutFromContextMenu() {
		this.cutItems(this.selectionForContextMenu);};
	

Editor.prototype.copyFromContextMenu = function Editor_copyFromContextMenu() {
		this.copyItems(this.selectionForContextMenu);};
	

Editor.prototype.pasteFromContextMenu = function Editor_pasteFromContextMenu() {
		this.pasteInNode(this.selectionForContextMenu[0].node);};
	

Editor.prototype.deleteFromContextMenu = function Editor_deleteFromContextMenu() {
		this.deleteItems(this.selectionForContextMenu);};
	

Editor.prototype.duplicateFromContextMenu = function Editor_duplicateFromContextMenu() {
		this.duplicateItems(this.selectionForContextMenu, true);};
	

Editor.prototype.ungroupFromContextMenu = function Editor_ungroupFromContextMenu() {
		this.ungroupItems(this.selectionForContextMenu);};
	

Editor.prototype.groupFromContextMenu = function Editor_groupFromContextMenu() {
		this.groupItems(this.selectionForContextMenu);};
	
	
Editor.prototype.editGroupFromContextMenu = function Editor_editGroupFromContextMenu() {
		this.beginEditingSubview(this.selectionForContextMenu[0]);};
	

Editor.prototype.lockFromContextMenu = function Editor_lockFromContextMenu() {
		if (Array.isArray(this.selectionForContextMenu)) this.selectionForContextMenu.every(function (obj) {
			this.lockObject(obj);return true; }, this);
		};
	

Editor.prototype.unlockFromContextMenu = function Editor_unlockFromContextMenu() {
		if (Array.isArray(this.selectionForContextMenu)) this.selectionForContextMenu.every(function (obj) {
			this.unlockObject(obj);return true; }, this);
		};
	


	
	
Editor.prototype.toggleSimulatedSystem = function Editor_toggleSimulatedSystem() {

		var editedScene = this.editedScene;
		this.closeItem();
		var newVersion = (this.context.projectContext.simulatedSystemVersion === 6) ? 7 : 6;
		this.context.projectContext.simulatedSystemVersion = newVersion;
		this.openItem(editedScene, { keepHistory: true });
		this.contentFrameController.simulatedSystemDidChange();};
	
	

	

Editor.prototype.navigateToSceneWithID = function Editor_navigateToSceneWithID(sceneID, inputData, dataSource, indexPath) {

		var scene = this.context.projectContext.sceneWithID(sceneID);
		if (scene) {
			this.closeItem();
			if (inputData) scene.loadInputData(inputData, dataSource, indexPath);
			this.openItem(scene, { keepHistory: true });
			if (scene.navigationBar) scene.navigationBar.addBackButtonIfEmpty();
		}};
	
	
Editor.prototype.goBack = function Editor_goBack() {
		return this.historyManager.goBack();};
	

Editor.prototype.goForward = function Editor_goForward() {
		return this.historyManager.goForward();};
	
	
	
	
	
Editor.prototype.checkSpecialNodes = function Editor__checkSpecialNodes() {
		if (this.editedScene)
			this.editedScene.checkSpecialNodes();};
	
	
	
	
Editor.prototype.refreshInspector = function Editor__refreshInspector(sender) {
		if (!this.inspector) return;
		this.inspector.updateCurrentSegment(true);};
	
	
	
	
	
	var detailButton, editCellButton;
	function showDetailButtonInCell(cell) {
	
		var itemsView = cell.itemsView;
		
		if (!itemsView || itemsView.locked || cell.locked ||
			_context.editor.editedSubview === cell)
			return;

		if (itemsView.UTI === 'appdoo.iOS.UITableView') {
			editCellButton.sprite = _context.pathForResource('EditRowButton.png');
			editCellButton.toolTip = LocalizedString1('Edit %1', (cell.contentView ? cell.contentView.readableValue : cell.readableValue));
		} else {
			editCellButton.sprite = _context.pathForResource('EditCellButton.png');
			editCellButton.toolTip = LocalizedString1('Edit %1', cell.readableValue);
		}

		var p = {
			top: cell.position.top + parseInt(cell.size.height/2) - 14,
			left: (cell.position.left||0) + cell.size.width - 29 - 6
		};
		
		var shouldShowDetailButton = (itemsView.detailSceneID && cell.indexPath) || cell.detailSceneID;
		if (shouldShowDetailButton) {
			cell.superview.addSubview(detailButton);
			detailButton.position = p;
			p.left -= 32;
			detailButton.cell = cell;
			detailButton.itemsView = itemsView;

			if (buttonsAreHidden) {
				detailButton.style({opacity:0, pointerEvents:'none'});
				setTimeout(function () {
					detailButton.style({opacity:1, pointerEvents:''});
				}, 250);
			}
			else detailButton.style({opacity:1, pointerEvents:''});
		} else {
			hideDetailButton();
		}

		cell.superview.addSubview(editCellButton);
		editCellButton.position = p;
		editCellButton.cell = cell;
		editCellButton.itemsView = itemsView;
		
		if (buttonsAreHidden) {
			editCellButton.style({opacity:0, pointerEvents:'none'});
			setTimeout(function () {
				editCellButton.style({opacity:1, pointerEvents:''});
			}, 250);
		}
		else editCellButton.style({opacity:1, pointerEvents:''});
		
		return true;
		
	}
	
	function hideButtons() {
		hideButton(detailButton);	
		hideButton(editCellButton);	
	}
	
	function hideDetailButton() {
		hideButton(detailButton);	
	}
	
	function hideEditCellButton() {
		hideButton(editCellButton);	
	}
	
	var to2, to3;
	function hideButton(b) {
	
		if (b && b.superview) {
			if (b.DOMNode.style.opacity === '0') {
				return b.removeFromSuperview(true);
			}
			b.beginAnimations();
			b.style({opacity:0});
			b.commitAnimations();
			if (to2)
				to3 = setTimeout(function () {
					b.removeFromSuperview(true);
				}, 250);
			else
				to2 = setTimeout(function () {
					b.removeFromSuperview(true);
				}, 250);
		}
		
	}

	var isOver, buttonsAreHidden = true;
Editor.prototype.addEditDetailButtonToCellInView = function Editor__addEditDetailButtonToCellInView(cell, itemsView) {

		if (cell._hasEditorEvents) return false;
		
		Object.defineProperty(cell, '_hasEditorEvents', {value: true, enumerable: false});
		Object.defineProperty(cell, 'itemsView', {value: itemsView, enumerable: false});

		if (!detailButton || !detailButton.DOMNode) {
			detailButton = createComponentFromDomain("SpriteButton", "Core.UI", this.context, {
				size: { width: 29, height: 29 },
				style: { cursor: 'default' },
				sprite: _context.pathForResource(_context.projectContext.simulatedSystemVersion < 7 ? 'DisclosureIndicatorButton.png' : 'DisclosureIndicatorButtonSystem7.png'), 
				action: function (e) {
	
					var indexPath = this.cell.indexPath,
						itemsView = this.itemsView,
						inputData = itemsView.usesDataSource ? itemsView.dataSource.dataForIndexPath(indexPath) : null,
						detailSceneID = this.cell.detailSceneID || itemsView.detailSceneID;
					
					_context.editor.navigateToSceneWithID(detailSceneID, inputData, itemsView.dataSource, indexPath);

					hideButtons();
	
				}})
			;

			detailButton.DOMNode.addEventListener('mouseover', function (e) {
				if (e.which) return; 
				isOver = true;
			});
		}

		if (!editCellButton || !editCellButton.DOMNode) {
		
			editCellButton = createComponentFromDomain("SpriteButton", "Core.UI", this.context, {
				size: { width: 29, height: 29 },
				style: { cursor: 'default' },
				action: function (e) {
	
					var indexPath = this.cell.indexPath,
						itemsView = this.cell.itemsView;
					
					if (indexPath && itemsView.editCellAtIndexPathWithEditor)
						itemsView.editCellAtIndexPathWithEditor(indexPath, _context.editor);
					else
						_context.editor.selectSingleObject(this.cell);

					hideButtons();
	
				}})
			;

			editCellButton.DOMNode.addEventListener('mouseover', function (e) {
				if (e.which) return;
				isOver = true;
			});
			
		}
		
		cell.DOMNode.addEventListener('mouseover', function (e) {
			if (e.which) return;
			
			if (showDetailButtonInCell.call(_context.editor, this)) {
				isOver = true;
				buttonsAreHidden = false;
			}
			
		}.bind(cell));

		var to;

		cell.DOMNode.addEventListener('mousemove', function (e) {
			if (to) { clearTimeout(to); to = null; }
			if (to2) { clearTimeout(to2); to2 = null; }
			if (to3) { clearTimeout(to3); to3 = null; }
			if (!isOver) return;
			if (showDetailButtonInCell.call(_context.editor, this)) {
				isOver = true;
				buttonsAreHidden = false;
			}
		}.bind(cell));


		var mouseOutFunc = function (e) {
			isOver = false;
			to = setTimeout(function () {
				if (!isOver) {
					if (!buttonsAreHidden) hideButtons();
					buttonsAreHidden = true;
				}
				to = null;
			}, 100);
		};
		
		cell.DOMNode.addEventListener('mouseout', mouseOutFunc);

		detailButton.DOMNode.addEventListener('mouseout', mouseOutFunc);
		editCellButton.DOMNode.addEventListener('mouseout', mouseOutFunc);
		
		itemsView = null;
		cell = null;
		
		return true;
		};
	


		
	
Editor.prototype.showFocusRing = function Editor_showFocusRing(obj) {
		if (!obj.editorFocusRing) {
			var focusRing = createComponentFromDomain("SmartScalingImage", "Core.UI", this.context, {
				imageSrc: 'Resources/SquaredFocusRing.png',
				contentInset: [11,11,11,11],
				style: { pointerEvents: 'none' },
				position: {
					left: -5,
					top: -5
				},})
			;
			Object.defineProperty(obj, 'editorFocusRing', { value: focusRing });
		}
		obj.editorFocusRing.size = {
			width: obj.size.width + 10,
			height: obj.size.height + 10
		};
		obj.addSubview(obj.editorFocusRing);};
	

Editor.prototype.hideFocusRing = function Editor_hideFocusRing(obj) {
		if (!obj.editorFocusRing) return;
		obj.editorFocusRing.removeFromSuperview(true);};
	

Editor.prototype.updateFocusRing = function Editor_updateFocusRing(obj) {
		if (!obj.editorFocusRing) return;
		obj.editorFocusRing.size = {
			width: obj.size.width + 10,
			height: obj.size.height + 10
		};
};
	
	

	
	
Editor.prototype.addDropHandlerToItemsView = function Editor_addDropHandlerToItemsView(itemsView) {

		var guidelineController;
	
		(function () {

		  this.dropHandler = {
		
			didEnterWithEvent: function (e) {
				guidelineController = _context.editor.manipulator.guidelineController;
				guidelineController.beginShowingGuidelines(true);
			}.bind(this),

			didLeaveWithEvent: function (e) {
				_context.editor.unhighlightView(this);
				return;
				if (guidelineController) {
					guidelineController.endShowingGuidelines();
					guidelineController = null;
				}
			}.bind(this),
			
			dropEffectForEvent: function (e) {

				if (!e.dataTransfer.types)
					return 'none';

				if (e.dataTransfer.types.indexOf(_context.objectTreeDataType) !== -1) {
					updateGuidelineControllerWithEventInView(_context.editor, guidelineController, e, _context.editor.editedView);
					return 'move';
				}
				
				if (e.dataTransfer.types.indexOf(_context.objectBlueprintDataType) !== -1) {
					var data = JSON.parse(e.dataTransfer.getData(_context.objectBlueprintDataType));

					if (data.UTI.indexOf('DataSource') !== -1) {
						_context.editor.highlightView(this);
						return 'move';
					}
					if (!_context.editor.objectIsAllowedToHaveMembersOfUTI(_context.editor.editedSubview, data.UTI) && data.isView) return 'none';
					else {
						_context.editor.highlightView(_context.editor.editedSubview);
						return 'move';
					}
				}
				
				if (e.dataTransfer.types.indexOf(_context.promisedRealObjectsDataType) !== -1) {
					var data = e.dataTransfer.getData(_context.promisedRealObjectsDataType);
					if (data.indexOf('DataSource') !== -1) {
						_context.editor.highlightView(this);
						return 'move';
					}
					else {
						return 'none';
					}
				}
				
				if (e.dataTransfer.files)
					return 'copy';
				
				return 'move';
			
			}.bind(this),
		
			didDropWithEvent: function (e) {
			
				_context.editor.unhighlightView(_context.editor.editedSubview);
				
				if (guidelineController) {
					guidelineController.endShowingGuidelines();
					guidelineController = null;
				}

				_context.editor.isPerformingDropOnItemView = true;
				
				var result = _context.editor.handleDrop(e, _context.editor.editedSubview);

				_context.editor.isPerformingDropOnItemView = false;

				if (result && result.identify && result.dataForItemInSectionAtIndex) {
					e.preventDefault();
					this.dataController.setValueForKey(result.identify(), 'e_dataSourceID');
					this.dataSourceDidChange();
					_context.editor.refreshInspector();
				}

				
				return result;

			}.bind(this),
		
		};
		
		}).call(itemsView);
	};
	
	
Editor.prototype.convertItemsToButton = function Editor_convertItemsToButton(items, setSelected) {

		var autoresizingMask = items[0].autoresizingMask;
		if (items.length === 1) {
			items[0].dataController.setValueForKey(18, 'autoresizingMask');
		}
		var button = this.groupItems(items, 'info.appdoo-mac.ButtonWithSubviews', setSelected !== false);
		button.autoresizingMask = autoresizingMask;
		return button;
		};
	

Editor.prototype.outlineAccessoryTypeDidChangeForItem = function Editor__outlineAccessoryTypeDidChangeForItem(item) {};
	
	
Editor.prototype.injectSpecialMethodsToEditedObject = function Editor__injectSpecialMethodsToEditedObject(obj) {
	
		if (!obj.hasOwnProperty('outlineAccessoryType')) {
			Object.defineProperty(obj, 'outlineAccessoryType', {
				get: function () {
					if (!this._outlineAccessoryType) {
						var t = '';
						if (this.locked) t += 'locked ';
						if (this.canReload) t += 'reload ';
						if (this.canPlay) t += 'play ';
						if (this.bindings && this.bindings.length) t += 'bound ';
						Object.defineProperty(this, '_outlineAccessoryType', {configurable:true,value:t});
					}
					return this._outlineAccessoryType;
				}
			});
			Object.defineProperty(obj, 'outlineAccessoryWidth', {
				get: function () {
					if (!this._outlineAccessoryWidth) {
						var width = 0;
						var defaultItemWidth = 16;
						if (typeof this.outlineAccessoryType === 'string') {
							if (Array.isArray(this.outlineAccessoryType.split(' '))) this.outlineAccessoryType.split(' ').every(function (s) {
								if (s === 'reload') width += defaultItemWidth;
								if (s === 'locked') width += defaultItemWidth;
								if (s === 'bound') width += defaultItemWidth;
								if (s === 'play') width += defaultItemWidth;return true; }, this);
							
						}
						Object.defineProperty(this, '_outlineAccessoryWidth', {configurable:true,value:width});
						return width;
					}
					return this._outlineAccessoryWidth;
				}
			});
			Object.defineProperty(obj, 'e_locked', {
				get: function () { return this.locked; },
				set: function (v) { _context.editor.setLockedStateForObject(v, this); }
			});
		}
		
		obj.outlineAccessoryTypeDidChange = function () {
			delete this._outlineAccessoryType;
			delete this._outlineAccessoryWidth;
			this.context.broadcastValueChangeForKeyPathInObject('outlineAccessoryType', this, this);
			this.context.broadcastValueChangeForKeyPathInObject('outlineAccessoryWidth', this, this);
		};
	};
	
	
Editor.prototype.lockObject = function Editor_lockObject(obj) {
		obj.dataController.setValueForKey(true, 'e_locked');};
	
	
Editor.prototype.unlockObject = function Editor_unlockObject(obj) {
		obj.dataController.setValueForKey(false, 'e_locked');};
	
	
Editor.prototype.setLockedStateForObject = function Editor__setLockedStateForObject(state, obj) {
		if (obj.locked === state) return false;
		obj.locked = state;
		obj.outlineAccessoryTypeDidChange();
		
		if (state) {
			this.manipulator.unregister(obj);
			this.treeController.unselectNode(obj.node);
		}
		else {
			this.manipulator.register(obj);
			if (this.treeController.nodeIsSelected(obj.node))
				this.manipulator.select(obj, this);
		}
		
		return true;};
	
	
	
	
	
Editor.prototype.changeTextSizeFromSelectionByStep = function Editor__changeTextSizeFromSelectionByStep(step) {
		var didChangeSomething = false;
		if (Array.isArray(this.selection.contents)) this.selection.contents.every(function (obj) {
			if ('fontSize' in obj) {
				obj.dataController.setValueForKey(obj.fontSize+step, 'fontSize');
				didChangeSomething = true;
			}return true; }, this);
		
		if (didChangeSomething) this.refreshInspector();};
	

Editor.prototype.toggleSelectedTextBoldness = function Editor__toggleSelectedTextBoldness(trueOrFalse) {
		this.toggleSelectedTextStyleState(trueOrFalse, fontIsBold, boldVariantForFont, nonboldVariantForFont);};
	

Editor.prototype.toggleSelectedTextItalicness = function Editor__toggleSelectedTextItalicness(trueOrFalse) {
		this.toggleSelectedTextStyleState(trueOrFalse, fontIsItalic, italicVariantForFont, nonitalicVariantForFont);};
	

Editor.prototype.toggleSelectedTextStyleState = function Editor__toggleSelectedTextStyleState(trueOrFalse, testStateFunc, trueStateFunc, falseStateFunc) {
		var wasInStateBefore = false;
		if (Array.isArray(this.selection.contents)) this.selection.contents.every(function (obj) {
			if ('fontName' in obj) {
				wasInStateBefore |= testStateFunc(obj.fontName);
			}return true; }, this);
		

		if (Array.isArray(this.selection.contents)) this.selection.contents.every(function (obj) {
			if ('fontName' in obj) {
				var newFontName;
				if (!wasInStateBefore) newFontName = trueStateFunc(obj.fontName);
				else newFontName = falseStateFunc(obj.fontName);
				obj.dataController.setValueForKey(newFontName, 'fontName');
			}return true; }, this);
		
		
		this.refreshInspector();};
	

Editor.prototype.isActionClick = function Editor_isActionClick(e) {
		return e && e.altKey && e.metaKey && !e.shiftKey;};
	
	
Editor.prototype.itemAcceptsMemberWithUTI = function Editor_itemAcceptsMemberWithUTI(item, UTI, data) {
		if (!item || !item.acceptsMemberWithUTI) return false;
		return item.acceptsMemberWithUTI(UTI, data);};
	
	
	Object.defineProperty(Editor.prototype, "selectedItem", {
		get: function () {
			if (this.selection.items.length === 1) return this.selection.items[0];
		}});
	
	
Editor.prototype.simulateAction = function Editor_simulateAction(PARAMETER_NOT_LONGER_USED, actionInfo, noBezel) {
		
		var actionType = actionInfo.actionType;

		if (actionType === 'showScene') {
			if (actionInfo.transfersDataAsInput) {
				var originalDataSource = this.context.projectContext.connectableObjects[actionInfo.transferDataSourceID];
				var inputData
				= originalDataSource.contents;
				this.navigateToSceneWithID(actionInfo.destinationSceneID, inputData, originalDataSource, null);
			}
			else {
				_context.editSceneWithID(actionInfo.destinationSceneID);
			}
		}
		else if (actionType === 'navigateBack') { _context.editor.goBack(); }
		else if (actionType === 'objectAction') { 
			var obj = this.context.projectContext.connectableObjects[actionInfo.objectID] || this.context.projectContext.globals[actionInfo.objectID];

			if (obj && obj.simulateAction) {

				obj.simulateAction(actionInfo.objectActionID);

				var objectActions = obj.performableActions;
				if (!objectActions || !actionInfo.objectActionID) return;
				
				if (!noBezel) {
					var info = objectActions[actionInfo.objectActionID];
					if (info)
					this.contentFrameController.showOnScreenInfo(info.name);
				}
			}
		}
	};
	

Editor.prototype.handleDblClickInsertion = function Editor__handleDblClickInsertion(uti, transferData, isView) {

		if (!this.validateInsertion(uti)) {
			this.context.beep();
			return false;
		}
		
		var dataTransfer = {
			data: transferData,
			getData: function (key) { return this.data[key]; },
			types: Object.keys(transferData)
		};

		if (isView)
			this.handleDrop({ dataTransfer: dataTransfer }, this.editedSubview);
		
		else {
		
			var d = transferData[this.context.objectBlueprintDataType];
			if (d) {
				var info = JSON.parse(d);
	
				var parentNode = !isView ? this.preferredObjectNodeForItemWithUTI(uti, info.properties) : null,
					result = this.insertFromBlueprint(uti, parentNode);
	
				if (result && info.properties) {
					for (var key in info.properties) {
						result[key] = info.properties[key];
					}
				}
			}
		}
	
		return true;};
	
	
Editor.prototype.showDataLinksAndHighlight = function Editor_showDataLinksAndHighlight(index) {
		if (this.inspector)
			this.inspector.showDataLinksAndHighlight(index);};
	
	
Editor.prototype.viewIsInsideButton = function Editor_viewIsInsideButton(view) {
		var superview = view;
		do {
			if (superview.UTI === 'info.appdoo-mac.ButtonWithSubviews')
				return true;
			superview = superview.superview;
		}
		while (superview && superview !== this.editedView);
		return false;};
	

Editor.prototype.showPrototypeDevicesBar = function Editor_showPrototypeDevicesBar(bar) {
		var containerView = this.contentFrameController.view;
		containerView.superview.addSubview(bar);
		var heightDiff = 0; 
		containerView.size.height = window.innerHeight - bar.size.height - heightDiff;};
	
	
Editor.prototype.prototypeDevicesBarDidChangeHeight = function Editor_prototypeDevicesBarDidChangeHeight(bar) {
		if (!bar.superview) return;
		
		var siblingView = bar.superview.subviews[0];
		var newHeigt = window.innerHeight - bar.size.height;
		var difference = siblingView.size.height - newHeigt;
		siblingView.size.height = newHeigt;
		siblingView.style({ webkitTransform:'translateY('+difference/2+'px)' });
		bar.style({ webkitTransform:'translateY('+(difference)+'px)' });

		var animationTime = bar.size.height > 0 ? .75 : 0.5;
		setTimeout(function () {
			siblingView.beginAnimations();
			siblingView.animationDuration = animationTime;
			siblingView.style({ webkitTransform:'' });
			siblingView.commitAnimations();
			bar.beginAnimations();
			bar.animationDuration = animationTime;
			bar.style({ webkitTransform:'' });
			bar.commitAnimations();
		}, 1);
		};
	
	
Editor.prototype.getRelativeXRespectingOriginalSuperview = function Editor_getRelativeXRespectingOriginalSuperview(_view, x, outerView) {
		this.pauseSubviewEditing();
		var result = _view.getRelativeX(x, outerView);
		this.resumeSubviewEditing();
		return result;};
	

Editor.prototype.getRelativeYRespectingOriginalSuperview = function Editor_getRelativeYRespectingOriginalSuperview(_view, y, outerView) {
		this.pauseSubviewEditing();
		var result = _view.getRelativeY(y, outerView);
		this.resumeSubviewEditing();
		return result;};
	
	
Editor.prototype.registerStateModifier = function Editor_registerStateModifier(obj) {
		if (!this.stateModifiers) this.stateModifiers = [];
		this.stateModifiers.push(obj);};
	

Editor.prototype.unregisterStateModifier = function Editor_unregisterStateModifier(obj) {
		this.stateModifiers.splice(this.stateModifiers.indexOf(obj));
		obj.restoreState();};
	
	
Editor.prototype.fileReferencesDidUpdate = function Editor_fileReferencesDidUpdate(refs) {
	
		function worker(obj) {
			if (obj && obj.fileReferenceDidUpdate) {
				if (Array.isArray(refs)) refs.every(function (ref) {
					obj.fileReferenceDidUpdate(ref);return true; }, this);
				
			}
		}

		updateSubviewsWithCallback(this.editedView, function (view) {
			worker(view);
		});
		
		if (Array.isArray(this.context.projectContext.project.objects)) this.context.projectContext.project.objects.every(function (obj) {
			worker(obj);return true; }, this);
		

		if (Array.isArray(this.context.projectContext.project.scenes)) this.context.projectContext.project.scenes.every(function (scene) {
			if (Array.isArray(scene.objects)) scene.objects.every(function (obj) {
				worker(obj);return true; }, this);
			
			worker(scene.navigationBar);return true; }, this);
		
		
		worker(this.contentFrameController.tabBar);
		this.refreshInspector();};
	

Editor.prototype.setValueWithoutUndoSupport = function Editor__setValueWithoutUndoSupport(item, value, keyPath) {

		if (item.dataController) {
			if (_context.undoManager)
				_context.undoManager.disableRegistration();
	
			item.dataController.setValueForKeyPath(value, keyPath, item.dataController);
			_context.editor.updateLayout();
	
			if (_context.undoManager)
				_context.undoManager.enableRegistration();
		}
		else
			item.setValueForKeyPath(value, keyPath);
	};
	
	
Editor.prototype.initPropertiesFromData = function Editor_initPropertiesFromData(data) {
try { __super.prototype.initPropertiesFromData.call(this, data); } catch (err) {}
if (data.hasOwnProperty("historyManager")) this.historyManager = data.historyManager;
if (data.hasOwnProperty("inspector")) this.inspector = data.inspector;
if (data.hasOwnProperty("overview")) this.overview = data.overview;
if (data.hasOwnProperty("selection")) this.selection = data.selection;
if (data.hasOwnProperty("searchField")) this.searchField = data.searchField;
if (data.hasOwnProperty("contentFrameController")) this.contentFrameController = data.contentFrameController;
if (data.hasOwnProperty("treeController")) this.treeController = data.treeController;
if (data.hasOwnProperty("mainSplitView")) this.mainSplitView = data.mainSplitView;
if (data.hasOwnProperty("devicePopupButton")) this.devicePopupButton = data.devicePopupButton;
if (data.hasOwnProperty("rightSplitView")) this.rightSplitView = data.rightSplitView;
if (data.hasOwnProperty("outlineViewContainer")) this.outlineViewContainer = data.outlineViewContainer;
if (data.hasOwnProperty("projectScenesController")) this.projectScenesController = data.projectScenesController;
if (data.hasOwnProperty("editorSourceView")) this.editorSourceView = data.editorSourceView;
if (data.hasOwnProperty("dataContextsController")) this.dataContextsController = data.dataContextsController;
if (data.hasOwnProperty("newItemListDataSource")) this.newItemListDataSource = data.newItemListDataSource;
};

Editor.prototype.decodeData = function Editor_decodeData(data) { var decoded;
try { decoded = __super.prototype.decodeData.call(this, data); } catch (err) { console.warn(err); decoded = clone(data); }
return decoded; };

Editor.prototype.encode = function Editor_encode() { var encoded;
try { encoded = __super.prototype.encode.call(this); } catch (err) { console.warn(err); encoded = this.context.encodeObject(this); }
return encoded; };

Editor.prototype.encodeCloned = function Editor_encodeCloned() { var encoded;
try { encoded = __super.prototype.encodeCloned.call(this); } catch (err) { console.warn(err); encoded = {}; }
return encoded; };

Editor.prototype.expectedTypeForProperty = function Editor_expectedTypeForProperty(key) {
	if (key === "historyManager") return "";
	if (key === "inspector") return "";
	if (key === "overview") return "";
	if (key === "selection") return "";
	if (key === "searchField") return "";
	if (key === "contentFrameController") return "";
	if (key === "treeController") return "";
	if (key === "mainSplitView") return "";
	if (key === "devicePopupButton") return "";
	if (key === "rightSplitView") return "";
	if (key === "outlineViewContainer") return "";
	if (key === "visibleOutlineView") return "";
	if (key === "projectScenesController") return "";
	if (key === "editorSourceView") return "";
	if (key === "dataContextsController") return "";
	if (key === "newItemListDataSource") return "";
	if (key === "editedView") return "";
	if (key === "editedViewController") return "";
	if (key === "objectsNode") return "";
	if (key === "navigationObjectsNode") return "";
	if (key === "suggestedMinimumTopPosition") return "";
	if (key === "suggestedMinimumLeftPosition") return "";
	if (key === "isInSubviewEditingMode") return "";
	if (key === "editedSubviewRect") return "";
	if (key === "destinationNodeForPasteOperation") return "";
	if (key === "bindableProperties") return "";
	if (key === "bindableObjects") return "";
	if (key === "currentZoomIsOriginalSize") return "";
	if (key === "providesBindableData") return "";
	if (key === "layoutRelationTargets") return "";
	if (key === "inspectorIsVisible") return "";
	if (key === "elementListIsVisible") return "";
	if (key === "newItemsList") return "";
	if (key === "newItemsListContainer") return "";
	if (key === "selectedItem") return "";
	if (__super) return __super.prototype.expectedTypeForProperty(key);
};

return Editor; }()));
registerType('appdoo', (function () { function EditorNavigationHistoryManager() {} var __super = setSupertypeFromDomain(EditorNavigationHistoryManager, 'BasicObject', 'Core');

EditorNavigationHistoryManager.prototype.init = function EditorNavigationHistoryManager_init() {
		__super.prototype.init.call(this);
		this.stack = [];
		this.stackPosition = 0;
		return this;};
	

	Object.defineProperty(EditorNavigationHistoryManager.prototype, "stack", {
	outlet: true, 
	enumerable: true, get:function () { return this._stack; }, set:function (v) {if (!Object.hasOwnProperty(this, "_stack")) Object.defineProperty(this, "_stack", { writable: true, configurable: true }); this._stack = v; }});
	

	Object.defineProperty(EditorNavigationHistoryManager.prototype, "stackPosition", {
	outlet: true, 
	enumerable: true, get:function () { return this._stackPosition; }, set:function (v) {if (!Object.hasOwnProperty(this, "_stackPosition")) Object.defineProperty(this, "_stackPosition", { writable: true, configurable: true }); this._stackPosition = v; }});
	

	Object.defineProperty(EditorNavigationHistoryManager.prototype, "editor", {
	outlet: true, 
	enumerable: true, get:function () { return this._editor; }, set:function (v) {if (!Object.hasOwnProperty(this, "_editor")) Object.defineProperty(this, "_editor", { writable: true, configurable: true }); this._editor = v; }});
	

	Object.defineProperty(EditorNavigationHistoryManager.prototype, "canGoBack", {
	synthesized: true, 
	observable: true, get:function () { return this._canGoBack; }, set:function (v) {if (!Object.hasOwnProperty(this, "_canGoBack")) Object.defineProperty(this, "_canGoBack", { writable: true, configurable: true }); this._canGoBack = v; this.context.broadcastValueChangeForKeyPathInObject("canGoBack", this, this);}});
	

	Object.defineProperty(EditorNavigationHistoryManager.prototype, "canGoForward", {
	synthesized: true, 
	observable: true, get:function () { return this._canGoForward; }, set:function (v) {if (!Object.hasOwnProperty(this, "_canGoForward")) Object.defineProperty(this, "_canGoForward", { writable: true, configurable: true }); this._canGoForward = v; this.context.broadcastValueChangeForKeyPathInObject("canGoForward", this, this);}});
	

EditorNavigationHistoryManager.prototype.push = function EditorNavigationHistoryManager_push(item) {

		if (this.isGoingBack) return;
		if (this.stack[this.stackPosition] === item.$id) { this.updateState(); return; }
		
		if (this.stackPosition < this.stack.length-1) {
			this.stack.splice(this.stackPosition+1, 10000);
		}
		
		this.stack.push(item.$id);

		this.stackPosition = this.stack.length-1;
		this.updateState();
		};
	
	
EditorNavigationHistoryManager.prototype.goBack = function EditorNavigationHistoryManager_goBack() {

		if (this.stackPosition <= 0) return;

		this.go(-1, function () {
			this.stack.splice(this.stackPosition, 1);
			this.goBack();
		}.bind(this));

		return true;};
	

EditorNavigationHistoryManager.prototype.goForward = function EditorNavigationHistoryManager_goForward() {
	
		if (this.stackPosition >= this.stack.length-1) return;
		
		this.go(+1, function () {
			this.stack.splice(this.stackPosition, 1);
			if (this.stackPosition > 0) this.stackPosition--;
			this.goForward();
		}.bind(this));
		
		return true;};
	
	
EditorNavigationHistoryManager.prototype.go = function EditorNavigationHistoryManager__go(direction, onMissingScene) {
		
		this.stackPosition += direction;
		var sceneID = this.stack[this.stackPosition];

		this.isGoingBack = true;

		var scene = this.context.projectContext.sceneWithID(sceneID);
		if (!scene) {
			 alertd('Screen missing:', sceneID, 'this.stackPosition:', this.stackPosition);
			this.isGoingBack = false;
			onMissingScene();
			return;
		}
		
		this.editor.closeItem();
		this.editor.openItem(scene);

		this.isGoingBack = false;
		this.updateState();};
	
	
EditorNavigationHistoryManager.prototype.updateState = function EditorNavigationHistoryManager__updateState() {
		this.canGoBack = this.stackPosition > 0;
		this.canGoForward = this.stackPosition < this.stack.length-1;};
	

EditorNavigationHistoryManager.prototype.initPropertiesFromData = function EditorNavigationHistoryManager_initPropertiesFromData(data) {
try { __super.prototype.initPropertiesFromData.call(this, data); } catch (err) {}
if (data.hasOwnProperty("stack")) this.stack = data.stack;
if (data.hasOwnProperty("stackPosition")) this.stackPosition = data.stackPosition;
if (data.hasOwnProperty("editor")) this.editor = data.editor;
};

EditorNavigationHistoryManager.prototype.decodeData = function EditorNavigationHistoryManager_decodeData(data) { var decoded;
try { decoded = __super.prototype.decodeData.call(this, data); } catch (err) { console.warn(err); decoded = clone(data); }
if (data.hasOwnProperty("editor")) decoded.editor = this.context.decodeObjectTree(data.editor);
return decoded; };

EditorNavigationHistoryManager.prototype.encode = function EditorNavigationHistoryManager_encode() { var encoded;
try { encoded = __super.prototype.encode.call(this); } catch (err) { console.warn(err); encoded = this.context.encodeObject(this); }
if (this._editor && this._editor.encode) {encoded.editor = this.editor.encode();
}return encoded; };

EditorNavigationHistoryManager.prototype.encodeCloned = function EditorNavigationHistoryManager_encodeCloned() { var encoded;
try { encoded = __super.prototype.encodeCloned.call(this); } catch (err) { console.warn(err); encoded = {}; }
if (this._editor && this._editor.encode) {encoded.editor = this.editor.encodeCloned();
}return encoded; };

EditorNavigationHistoryManager.prototype.expectedTypeForProperty = function EditorNavigationHistoryManager_expectedTypeForProperty(key) {
	if (key === "stack") return "Array";
	if (key === "stackPosition") return "Number";
	if (key === "editor") return "Editor";
	if (key === "canGoBack") return "Boolean";
	if (key === "canGoForward") return "Boolean";
	if (__super) return __super.prototype.expectedTypeForProperty(key);
};

return EditorNavigationHistoryManager; }()));