Bug 401914 - Improve Editor Theming
diff --git a/bundles/org.eclipse.orion.client.editor/web/orion/editor/textTheme.js b/bundles/org.eclipse.orion.client.editor/web/orion/editor/textTheme.js
index e4cc33d..a16ff2f 100644
--- a/bundles/org.eclipse.orion.client.editor/web/orion/editor/textTheme.js
+++ b/bundles/org.eclipse.orion.client.editor/web/orion/editor/textTheme.js
@@ -34,13 +34,15 @@
 		this._document = options.document || document;

 	}

 	

-	var DefaultTheme;

-	TextTheme.getTheme = function() {

-		if (!DefaultTheme) {

+	var Themes = {};

+	TextTheme.getTheme = function(name) {

+		name = name || "default";

+		var theme = Themes[name];

+		if (!theme) {

 			//TODO: Load a default sheet somehow

-			DefaultTheme = new TextTheme();

+			theme = Themes[name] = new TextTheme();

 		}

-		return DefaultTheme;

+		return theme;

 	};

 

 	TextTheme.prototype = /** @lends orion.editor.TextTheme.prototype */ {

diff --git a/bundles/org.eclipse.orion.client.git/web/git/git-commit.js b/bundles/org.eclipse.orion.client.git/web/git/git-commit.js
index d58ca9a..2ec5ba3 100644
--- a/bundles/org.eclipse.orion.client.git/web/git/git-commit.js
+++ b/bundles/org.eclipse.orion.client.git/web/git/git-commit.js
@@ -15,8 +15,9 @@
 
 define([ 'i18n!git/nls/gitmessages', 'require', 'orion/bootstrap', 'orion/status', 'orion/progress', 'orion/commands', 'orion/dialogs', 'orion/selection',
 		'orion/fileClient', 'orion/operationsClient', 'orion/searchClient', 'orion/globalCommands', 'orion/git/gitCommitExplorer', 'orion/git/gitCommands',
+		'orion/widgets/themes/ThemePreferences', 'orion/widgets/themes/editor/ThemeData',
 		'orion/git/gitClient', 'orion/links', 'orion/contentTypes', 'orion/PageUtil' ], function(messages, require, mBootstrap, mStatus, mProgress, mCommands,
-		mDialogs, mSelection, mFileClient, mOperationsClient, mSearchClient, mGlobalCommands, mGitCommitExplorer, mGitCommands, mGitClient, mLinks,
+		mDialogs, mSelection, mFileClient, mOperationsClient, mSearchClient, mGlobalCommands, mGitCommitExplorer, mGitCommands, mThemePreferences, mThemeData, mGitClient, mLinks,
 		mContentTypes, PageUtil) {
 
 	mBootstrap.startup().then(
@@ -32,6 +33,9 @@
 				new mStatus.StatusReportingService(serviceRegistry, operationsClient, "statusPane", "notifications", "notificationArea"); //$NON-NLS-2$ //$NON-NLS-1$ //$NON-NLS-0$
 				new mProgress.ProgressService(serviceRegistry, operationsClient);
 
+				var themePreferences = new mThemePreferences.ThemePreferences(preferences, new mThemeData.ThemeData());
+				themePreferences.apply();
+		
 				// ...
 				var linkService = new mLinks.TextLinkService({ serviceRegistry : serviceRegistry
 				});
diff --git a/bundles/org.eclipse.orion.client.git/web/git/git-status2.js b/bundles/org.eclipse.orion.client.git/web/git/git-status2.js
index 2838682..c0b3489 100644
--- a/bundles/org.eclipse.orion.client.git/web/git/git-status2.js
+++ b/bundles/org.eclipse.orion.client.git/web/git/git-status2.js
@@ -15,9 +15,10 @@
 
 define(['i18n!git/nls/gitmessages', 'require', 'orion/bootstrap', 'orion/status', 'orion/progress', 'orion/commands', 'orion/dialogs', 'orion/selection',
 	'orion/fileClient', 'orion/operationsClient', 'orion/searchClient', 'orion/globalCommands',
+	'orion/widgets/themes/ThemePreferences', 'orion/widgets/themes/editor/ThemeData',
 	'orion/git/gitStatusExplorer', 'orion/git/gitCommands', 'orion/git/gitClient', 'orion/ssh/sshTools', 'orion/links', 'orion/contentTypes', 'orion/PageUtil'],
 	function(messages, require, mBootstrap, mStatus, mProgress, mCommands, mDialogs, mSelection,
-		mFileClient, mOperationsClient, mSearchClient, mGlobalCommands,
+		mFileClient, mOperationsClient, mSearchClient, mGlobalCommands, mThemePreferences, mThemeData,
 		mGitStatusExplorer, mGitCommands, mGitClient, mSshTools, mLinks, mContentTypes, PageUtil) {
 
 	mBootstrap.startup().then(function(core) {
@@ -31,6 +32,9 @@
 		new mStatus.StatusReportingService(serviceRegistry, operationsClient, "statusPane", "notifications", "notificationArea"); //$NON-NLS-2$ //$NON-NLS-1$ //$NON-NLS-0$
 		new mProgress.ProgressService(serviceRegistry, operationsClient);
 
+		var themePreferences = new mThemePreferences.ThemePreferences(preferences, new mThemeData.ThemeData());
+		themePreferences.apply();
+		
 		// ...
 		var linkService = new mLinks.TextLinkService({serviceRegistry: serviceRegistry});
 		var gitClient = new mGitClient.GitService(serviceRegistry);
diff --git a/bundles/org.eclipse.orion.client.ui/web/compare/compare.js b/bundles/org.eclipse.orion.client.ui/web/compare/compare.js
index 0a34d50..5665087 100644
--- a/bundles/org.eclipse.orion.client.ui/web/compare/compare.js
+++ b/bundles/org.eclipse.orion.client.ui/web/compare/compare.js
@@ -12,8 +12,9 @@
 /*global define document */
 
 define(['orion/bootstrap', 'orion/status', 'orion/progress', 'orion/operationsClient', 'orion/commands', 'orion/fileClient', 'orion/searchClient', 'orion/globalCommands',
-		'orion/compare/compare-features', 'orion/compare/compare-container', 'orion/compare/compareUtils', 'orion/contentTypes', 'orion/PageUtil'],
-		function(mBootstrap, mStatus, mProgress, mOperationsClient, mCommands, mFileClient, mSearchClient, mGlobalCommands, mCompareFeatures, mCompareContainer, mCompareUtils, mContentTypes, PageUtil) {
+		'orion/compare/compare-features', 'orion/compare/compare-container', 'orion/widgets/themes/ThemePreferences', 'orion/widgets/themes/editor/ThemeData',
+        'orion/compare/compareUtils', 'orion/contentTypes', 'orion/PageUtil'],
+		function(mBootstrap, mStatus, mProgress, mOperationsClient, mCommands, mFileClient, mSearchClient, mGlobalCommands, mCompareFeatures, mCompareContainer, mThemePreferences, mThemeData, mCompareUtils, mContentTypes, PageUtil) {
 	mBootstrap.startup().then(function(core) {
 		var serviceRegistry = core.serviceRegistry;
 		var preferences = core.preferences;
@@ -30,6 +31,9 @@
 		var statusService = new mStatus.StatusReportingService(serviceRegistry, operationsClient, "statusPane", "notifications", "notificationArea"); //$NON-NLS-2$ //$NON-NLS-1$ //$NON-NLS-0$
 		var progressService = new mProgress.ProgressService(serviceRegistry, operationsClient);
 
+//		var themePreferences = new mThemePreferences.ThemePreferences(preferences, new mThemeData.ThemeData());
+//		themePreferences.apply();
+		
 		mGlobalCommands.generateBanner("orion-compare", serviceRegistry, commandService, preferences, searcher); //$NON-NLS-0$
 		var uiFactory = new mCompareFeatures.TwoWayCompareUIFactory({
 			parentDivID: "compareContainer", //$NON-NLS-0$
@@ -38,7 +42,7 @@
 		});
 		uiFactory.buildUI();
 		var diffProvider = new mCompareContainer.DefaultDiffProvider(serviceRegistry);
-		
+
 		var startWidget = function(){
 			var compareParams = PageUtil.matchResourceParameters();
 			var options = {
diff --git a/bundles/org.eclipse.orion.client.ui/web/edit/setup.js b/bundles/org.eclipse.orion.client.ui/web/edit/setup.js
index 9f04089..805cdaf 100644
--- a/bundles/org.eclipse.orion.client.ui/web/edit/setup.js
+++ b/bundles/org.eclipse.orion.client.ui/web/edit/setup.js
@@ -17,11 +17,12 @@
         'orion/problems', 'orion/editor/contentAssist', 'orion/editorCommands', 'orion/editor/editorFeatures', 'orion/editor/editor', 'orion/syntaxchecker',
         'orion/editor/textView', 'orion/editor/textModel', 
         'orion/editor/projectionTextModel', 'orion/keyBinding','orion/searchAndReplace/textSearcher',
-        'orion/edit/dispatcher', 'orion/contentTypes', 'orion/PageUtil', 'orion/highlight', 'orion/i18nUtil', 'orion/edit/syntaxmodel', 'orion/widgets/themes/editor/MiniThemeChooser'],
+        'orion/edit/dispatcher', 'orion/contentTypes', 'orion/PageUtil', 'orion/highlight', 'orion/i18nUtil', 'orion/edit/syntaxmodel',
+        'orion/widgets/themes/ThemePreferences', 'orion/widgets/themes/editor/ThemeData', 'orion/widgets/themes/editor/MiniThemeChooser'],
 		function(messages, require, Deferred, lib, mSelection, mStatus, mProgress, mDialogs, mCommands, mFavorites, mExtensionCommands,
 				mFileClient, mOperationsClient, mSearchClient, mGlobalCommands, mOutliner, mProblems, mContentAssist, mEditorCommands, mEditorFeatures, mEditor,
 				mSyntaxchecker, mTextView, mTextModel, mProjectionTextModel, mKeyBinding, mSearcher,
-				mDispatcher, mContentTypes, PageUtil, Highlight, i18nUtil, SyntaxModelWirer, mThemeChooser) {
+				mDispatcher, mContentTypes, PageUtil, Highlight, i18nUtil, SyntaxModelWirer, mThemePreferences, mThemeData, mThemeChooser) {
 	
 var exports = exports || {};
 	
@@ -144,7 +145,9 @@
 							name = self.getTitle();
 						}
 		
-						var chooser = new mThemeChooser.MiniThemeChooser( preferences );
+						var themePreferences = new mThemePreferences.ThemePreferences(preferences, new mThemeData.ThemeData());
+						themePreferences.apply();
+						var chooser = new mThemeChooser.MiniThemeChooser( themePreferences );
 						mGlobalCommands.addSettings( chooser );
 						
 						mGlobalCommands.setPageTarget({task: "Coding", name: name, target: metadata,  //$NON-NLS-0$
diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/globalCommands.js b/bundles/org.eclipse.orion.client.ui/web/orion/globalCommands.js
index 6cc533b..dfe6d77 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/globalCommands.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/globalCommands.js
@@ -14,11 +14,11 @@
 
 define(['i18n!orion/nls/messages', 'require', 'orion/commonHTMLFragments', 'orion/commands', 'orion/parameterCollectors', 
 	'orion/extensionCommands', 'orion/uiUtils', 'orion/keyBinding', 'orion/breadcrumbs', 'orion/webui/littlelib', 'orion/webui/splitter', 
-	'orion/webui/dropdown', 'orion/webui/tooltip', 'orion/favorites', 'orion/contentTypes', 'orion/URITemplate', 'orion/PageUtil', 'orion/widgets/themes/container/ThemeSheetWriter', 
+	'orion/webui/dropdown', 'orion/webui/tooltip', 'orion/favorites', 'orion/contentTypes', 'orion/URITemplate', 'orion/PageUtil', 'orion/widgets/themes/ThemePreferences', 'orion/widgets/themes/container/ThemeData', 
 	'orion/searchUtils', 'orion/inputCompletion/inputCompletion', 'orion/globalSearch/advSearchOptContainer', 'orion/Deferred',
 	'orion/widgets/UserMenu', 'orion/PageLinks', 'orion/webui/dialogs/OpenResourceDialog', 'text!orion/banner/banner.html', 'text!orion/banner/footer.html', 'text!orion/banner/toolbar.html'], 
         function(messages, require, commonHTML, mCommands, mParameterCollectors, mExtensionCommands, mUIUtils, mKeyBinding, mBreadcrumbs, lib, mSplitter, 
-        mDropdown, mTooltip, mFavorites, mContentTypes, URITemplate, PageUtil, ThemeSheetWriter, mSearchUtils, mInputCompletion, 
+        mDropdown, mTooltip, mFavorites, mContentTypes, URITemplate, PageUtil, mThemePreferences, mThemeData, mSearchUtils, mInputCompletion, 
         mAdvSearchOptContainer, Deferred, mUserMenu, PageLinks, openResource, BannerTemplate, FooterTemplate, ToolbarTemplate){
 
 	/**
@@ -439,43 +439,6 @@
 		});
 	}
 	
-	
-	function applyTheme(preferences){
-	
-		preferences.getPreferences('/themes', 2).then(function(prefs){ //$NON-NLS-0$
-			
-			var selected = prefs.get( 'selected' ); //$NON-NLS-0$
-			
-			if( selected ){
-				var ob = JSON.parse( selected );
-				
-				var stylesStr =  prefs.get( 'styles' ); //$NON-NLS-0$
-				if(!stylesStr){
-					return;
-				}
-				var styles = JSON.parse(stylesStr);
-				
-				for( var theme in styles ){
-					
-					var cssdata;
-					
-					if( styles[theme].name === ob.selected ){
-						cssdata = styles[theme];
-						var sheetMaker = new ThemeSheetWriter.ThemeSheetWriter();
-						var css = sheetMaker.getSheet( cssdata );
-				
-						var stylesheet = document.createElement("STYLE"); //$NON-NLS-0$
-						stylesheet.appendChild(document.createTextNode(css));
-							
-						var head = document.getElementsByTagName("HEAD")[0] || document.documentElement; //$NON-NLS-0$
-						head.appendChild(stylesheet);	
-						break;
-					}	
-				}
-			}		
-		});
-	}
-	
 	function getToolbarElements(toolNode) {
 		var elements = {};
 		var toolbarNode = null;
@@ -615,7 +578,7 @@
 	 * @function
 	 */
 	function generateBanner(parentId, serviceRegistry, commandService, prefsService, searcher, handler, /* optional */ editor, /* optional */ escapeProvider) {
-		applyTheme( prefsService );
+		new mThemePreferences.ThemePreferences(prefsService, new mThemeData.ThemeData()).apply();
 		
 		var parent = lib.node(parentId);
 		
diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/settings/SettingsContainer.js b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/settings/SettingsContainer.js
index 2caf09f..75eefcb 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/settings/SettingsContainer.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/settings/SettingsContainer.js
@@ -18,13 +18,14 @@
 		'orion/PageUtil', 'orion/webui/littlelib', 'orion/objects', 'orion/URITemplate', 

 		'orion/widgets/themes/ThemeBuilder', 

 		'orion/settings/ui/PluginSettings', 

+		'orion/widgets/themes/ThemePreferences', 

 		'orion/widgets/themes/editor/ThemeData', 

 		'orion/widgets/themes/container/ThemeData', 

 		'orion/widgets/settings/SplitSelectionLayout',

 		'orion/widgets/plugin/PluginList',

 		'orion/widgets/settings/UserSettings'

 		], function(messages, require, mGlobalCommands, PageUtil, lib, objects, URITemplate, 

-			ThemeBuilder, SettingsList, editorThemeData, containerThemeData, SplitSelectionLayout, PluginList, UserSettings) {

+			ThemeBuilder, SettingsList, mThemePreferences, editorThemeData, containerThemeData, SplitSelectionLayout, PluginList, UserSettings) {

 

 	/**

 	 * @param {Object} options

@@ -122,8 +123,9 @@
 			}

 			

 			var containerTheme = new containerThemeData.ThemeData();

+			var themePreferences = new mThemePreferences.ThemePreferences(this.preferences, containerTheme);

 		

-			this.themeWidget = new ThemeBuilder({ commandService: this.commandService, preferences: this.preferences, themeData: containerTheme });

+			this.themeWidget = new ThemeBuilder({ commandService: this.commandService, preferences: themePreferences, themeData: containerTheme });

 			

 			lib.empty(this.table);

 

@@ -144,8 +146,9 @@
 			}

 			

 			var editorTheme = new editorThemeData.ThemeData();

+			var themePreferences = new mThemePreferences.ThemePreferences(this.preferences, editorTheme);

 		

-			this.editorThemeWidget = new ThemeBuilder({ commandService: this.commandService, preferences: this.preferences, themeData: editorTheme });

+			this.editorThemeWidget = new ThemeBuilder({ commandService: this.commandService, preferences: themePreferences, themeData: editorTheme });

 			

 			var command = { name:'Import', tip:'Import a theme', id:0, callback: editorTheme.importTheme.bind(editorTheme) };

 			

diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/ThemeBuilder.js b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/ThemeBuilder.js
index e1b77db..ee1d902 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/ThemeBuilder.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/ThemeBuilder.js
@@ -62,8 +62,6 @@
 			

 			this.themeData = args.themeData;

 			

-			this.processSettings = this.themeData.processSettings;

-		

 			init();	

 			

 			var commandTemplate = '<div id="commandButtons">' +

@@ -81,8 +79,6 @@
 			this.commandService = args.commandService;

 			this.preferences = args.preferences;

 					

-			this.initializeStorage();

-			

 			var revertCommand = new mCommands.Command({

 				name: 'Cancel',

 				tooltip: 'Revert Theme',

@@ -185,38 +181,6 @@
 

 		ThemeBuilder.prototype.colornames = colornames;

 		

-		

-		function initializeStorage(){

-		

-			var themeInfo = this.themeData.getThemeStorageInfo();

-			var themeData = this.themeData; 

-		

-			this.preferences.getPreferences( themeInfo.storage, 2).then(function(prefs){ 

-

-				/* Check to see if the Orion theme is in the themes preferences ... if it is, 

-				   then we don't need to populate again, otherwise we do need to populate. */

-

-				var styles = prefs.get( themeInfo.styleset ); 

-				if (!styles){

-					styles = themeData.getStyles();

-					prefs.put( themeInfo.styleset, JSON.stringify(styles) ); 

-				} else {

-					styles = JSON.parse ( styles );				

-				}

-				

-				var selectedTheme = prefs.get( 'selected' );

-				if ( selectedTheme ) { selectedTheme = JSON.parse(selectedTheme); }

-				if (!selectedTheme || selectedTheme[themeInfo.selectedKey] === undefined) {

-					selectedTheme = selectedTheme || {}; 

-					selectedTheme[themeInfo.selectedKey] = themeInfo.defaultTheme;

-					prefs.put( 'selected', JSON.stringify(selectedTheme) );

-				}

-				

-			} );

-		}

-		

-		ThemeBuilder.prototype.initializeStorage = initializeStorage;

-		

 		function addAdditionalCommand( commandData ){

 		

 			var commitMessageParameters = new mCommands.ParametersDescription(

@@ -698,50 +662,27 @@
 		

 		ThemeBuilder.prototype.drawOutlineData = drawOutlineData;

 		

-		function processSettings( settings, preferences ){ /* to be provided by ThemeData */ }

-		

-		ThemeBuilder.prototype.processSettings = processSettings;

-		

 		function apply(data){

 		

-			this.processSettings( this.settings, this.preferences );

-			

-			var themename = this.settings.name;

-			

-			var themeInfo = data.themeData.getThemeStorageInfo();

-			

-			var themeBuilder = this;

-			

 			/* New Theme defined */

-			this.preferences.getPreferences(themeInfo.storage, 2).then(function(prefs){ //$NON-NLS-0$

+			this.preferences.getTheme(function( themeStyles ) { 

+				var themename = this.settings.name;

 				

-				var styles = prefs.get(	themeInfo.styleset );

-				if( styles ){	

-					styles = JSON.parse( styles ); 

-				}

+				var styles = themeStyles.styles;

+

+				var themesaver = lib.node( 'themesaver' );

+				var name = themesaver.firstChild.value;

 					

-				if( lib.node( 'themesaver' ).firstChild.value.length > 0 ){

+				if( name.length > 0 ){

 				

-					var newtheme = {};

-					

-					newtheme.name = lib.node( 'themesaver' ).firstChild.value;

-					

-					for( var setting in themeBuilder.settings ){

-						

-						var element = themeBuilder.settings[setting].name;

-						

-						if( element !== 'name' ){

-							newtheme[element] = themeBuilder.settings[setting].value;

-						}

-					}

 					

 					var existingTheme = false;

 					

 					if( styles ){	

 						

-						for( var s in styles ){

+						for( var s=0; s<styles.length; s++ ){

 						

-							if( styles[s].name === newtheme.name ){

+							if( styles[s].name === name ){

 								existingTheme = true;

 								break;

 							}			

@@ -749,38 +690,43 @@
 					}

 					

 					if( !existingTheme ){

+						var newtheme = {};

+						

+						newtheme.name = name;

+						

+						for( var setting in this.settings ){

+							

+							var element = this.settings[setting].name;

+							

+							if( element !== 'name' ){

+								newtheme[element] = this.settings[setting].value;

+							}

+						}

 						styles.push( newtheme );

 					}

 					

-					themename = newtheme.name;

+					themename = name;

 					

-					if( lib.node( 'themesaver' ).value ){

-						lib.node( 'themesaver' ).value = '';

-					}

+					themesaver.firstChild.value = '';

 				}

 			

-				if (themeBuilder.fontSize) {

+				if (this.fontSize) {

 					for( var i=0; i<styles.length; i++ ){

-						styles[i].fontSize = themeBuilder.fontSize;

+						styles[i].fontSize = this.fontSize;

 					}

 				}

 				

-				var selectedTheme = prefs.get( 'selected' );

-				selectedTheme = selectedTheme ? JSON.parse( selectedTheme ) : {};

-				selectedTheme[themeInfo.selectedKey] = themename;

-				prefs.put( themeInfo.styleset, JSON.stringify(styles) );

-				prefs.put( 'selected', JSON.stringify(selectedTheme) );

+				this.preferences.setTheme(themename, styles);

 				lib.node( 'savecontainer' ).style.display = 'none';

 				lib.node( 'pickercontainer' ).style.display = '';

-				themeBuilder.updateThemePicker(themename, styles);

-				themeBuilder.AUTONAME = false;

-			} );

+				this.updateThemePicker(themename, styles);

+				this.AUTONAME = false;

+			}.bind(this) );

 		}

 		

 		ThemeBuilder.prototype.apply = apply;

 

 		function revert(data){	

-			this.initializeStorage();

 			this.guide();

 			lib.node( 'pickercontainer' ).style.display = '';

 			lib.node( 'savecontainer' ).style.display = 'none';

@@ -800,17 +746,19 @@
 		ThemeBuilder.prototype.guide = guide;

 		

 		function select( name, styles ){

-		

-			for( var s in styles ){

+		    

+		    for ( var theme = 0; theme<styles.length; theme++) {

 				

-				if( styles[s].name === name ){

-				    

-				    this.settings.name = name;

+				var style = styles[theme];

+				

+				if( style.name === name) {

+					

+		    		this.settings.name = name;

 					

 					for( var setting in this.settings ){

 						if( setting !== 'name' ){

 							var item = this.settings[setting].name;

-							this.settings[setting].value = styles[s][item];

+							this.settings[setting].value = style[item];

 						}

 					}

 					break;

@@ -863,133 +811,69 @@
 		

 		ThemeBuilder.prototype.updateFontSizePicker = updateFontSizePicker;

 		

-		function addFontSizePicker(){

+		function addFontSizePicker(themeStyles){

 		

-			var themebuilder = this;

+			var currentFont = themeStyles.style.fontSize;

 			

-			var themeInfo = this.themeData.getThemeStorageInfo();

+			var picker = document.getElementById( 'fontsizepicker' );

+	

+			var options = [];

 			

-			this.preferences.getPreferences(themeInfo.storage, 2).then(function(prefs){

-				var styles = prefs.get( themeInfo.styleset );

-				var selection = prefs.get( 'selected' );

-				if(selection){ selection = JSON.parse( selection ); }

-				var currentFont;

-				

-				if( styles ){	

-					styles = JSON.parse( styles );

+			for( var size = 8; size < 19; size++ ){

 					

-					for( var s = 0; s < styles.length; s++ ){

-						if( styles[s].name ===  selection[themeInfo.selectedKey] ){

-							currentFont = styles[s].fontSize;

-							break;

-						}

-					}

-				}

+				var set = {

+					value: size + 'pt',

+					label: size + 'pt'

+				};	

 				

-				var picker = document.getElementById( 'fontsizepicker' );

-		

-				var options = [];

+				if( set.value === currentFont ){ set.selected = 'true'; }

 				

-				for( var size = 8; size < 19; size++ ){

-						

-					var set = {

-						value: size + 'pt',

-						label: size + 'pt'

-					};	

-					

-					if( set.value === currentFont ){ set.selected = 'true'; }

-					

-					options.push(set);

-				}	

-				

-				if(!this.sizeSelect){

-					this.sizeSelect = new Select( {options:options}, picker );

-					this.sizeSelect.setStorageItem = themebuilder.selectFontSize.bind(themebuilder);	

-					this.sizeSelect.show();

-				}

-			});

+				options.push(set);

+			}	

 			

+			if(!this.sizeSelect){

+				this.sizeSelect = new Select( {options:options}, picker );

+				this.sizeSelect.setStorageItem = this.selectFontSize.bind(this);	

+				this.sizeSelect.show();

+			}

 		}

 		

 		ThemeBuilder.prototype.addFontSizePicker = addFontSizePicker;

 		

 		

-		function addThemePicker(){

+		function addThemePicker(themeStyles){

 		

 			var options = [];

 			

-			var themebuilder = this;

+			var name = themeStyles.style.name;

+			var styles = themeStyles.styles;

+			for( var theme= 0; theme < styles.length; theme++ ){

 			

-			var selection;

-			

-			var themeData = this.themeData;

-

-			var themeInfo = themeData.getThemeStorageInfo();

-			

-			this.preferences.getPreferences(themeInfo.storage, 2).then(function(prefs){ //$NON-NLS-0$

-

-				/* Check to see if the Orion theme is in the themes preferences ... if it is, 

-				   then we don't need to populate again, otherwise we do need to populate. */

-

-				selection = prefs.get( 'selected' );

+				var set = {

+					value: styles[theme].name,

+					label: styles[theme].name

+				};	

 				

-				if(selection){ selection = JSON.parse( selection ); }

-				

-				var styles = prefs.get( themeInfo.styleset );

-				

-				if(styles){ styles = JSON.parse( styles ); }

-

-				if(!styles){

-				

-					/* If we're in this condition, then the themes are not in local storage yet.

-					   Going to make sure */

-					styles = themeData.getStyles();

-					prefs.put( themeInfo.styleset, JSON.stringify(styles) ); 

+				if( styles[theme].name === name ){

+					set.selected = true;

 				}

 				

-				if(!selection) {

-					selection = {}; 

-					selection[themeInfo.selectedKey] = themeInfo.defaultTheme;

-					prefs.put( 'selected', JSON.stringify(selection) );

-				}

+				options.push(set);

+			}	

+				

+			this.select( name, styles );

 			

-				if( styles ){

-				

-					for( var theme in styles ){

-					

-						var set = {

-							value: styles[theme].name,

-							label: styles[theme].name

-						};	

-						

-						if( selection ){	

-							if( styles[theme].name === selection[themeInfo.selectedKey] ){

-								set.selected = true;

-							}

-						}

-						

-						options.push(set);

-						

-						themebuilder.styles = styles;

-					}	

-				}

-				

-				if( selection ){	

-					this.select( selection[themeInfo.selectedKey], styles );

-				}

+			var picker = document.getElementById( 'themepicker' );

 			

-				var picker = document.getElementById( 'themepicker' );

+			if(!this.themeSelect){

+				this.themeSelect = new Select( {options:options}, picker );

+				this.themeSelect.setStorageItem = this.selectTheme.bind( this );

+				this.themeSelect.show();

 				

-				if(!this.themeSelect){

-					this.themeSelect = new Select( {options:options}, picker );

-					this.themeSelect.setStorageItem = themebuilder.selectTheme.bind( themebuilder );

-					this.themeSelect.show();

-					

-					var saver = document.getElementById( 'themesaver' );

-					this.themeSaver = new TextField({}, saver );

-					this.themeSaver.show();

-				}

-			}.bind(this));	

+				var saver = document.getElementById( 'themesaver' );

+				this.themeSaver = new TextField({}, saver );

+				this.themeSaver.show();

+			}

 		}

 		

 		ThemeBuilder.prototype.addThemePicker = addThemePicker;

@@ -1059,9 +943,11 @@
 				lib.node( 'sizecontainer' ).style.display = '';   */

 			}

 	

-			this.drawOutlineData(data);	

-			this.addFontSizePicker();

-			this.addThemePicker();

+			this.drawOutlineData(data);

+			this.preferences.getTheme(function(themeStyles) {

+				this.addFontSizePicker(themeStyles);

+				this.addThemePicker(themeStyles);		

+			}.bind(this));

 			

 			this.commandService.renderCommands('themeCommands', document.getElementById( 'revertCommands' ), this, this, "button"); //$NON-NLS-1$ //$NON-NLS-0$		

 		}

@@ -1069,17 +955,9 @@
 		ThemeBuilder.prototype.renderData = renderData;

 		

 		function selectTheme ( name ) {

-			var builder = this;

-			var themeInfo = this.themeData.getThemeStorageInfo();

-			this.preferences.getPreferences(themeInfo.storage, 2).then(function(prefs){ //$NON-NLS-0$

-

-				var styles = prefs.get( themeInfo.styleset );

-				

-				if(styles){ 

-					styles = JSON.parse( styles ); 

-					builder.select( name, styles );

-				}

-			});

+			this.preferences.getTheme(function(themeStyles) {

+				this.select( name, themeStyles.styles );

+			}.bind(this));

 		}

 		

 		ThemeBuilder.prototype.selectTheme = selectTheme;

diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/container/ThemeData.js b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/container/ThemeData.js
index 134c97b..4fb7dc2 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/container/ThemeData.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/container/ThemeData.js
@@ -11,8 +11,8 @@
 /*global orion window console define localStorage*/

 /*jslint browser:true*/

 

-define(['orion/widgets/themes/container/ThemeSheetWriter'], 

-	function(ThemeSheetWriter) {

+define(['orion/editor/textTheme', 'orion/widgets/themes/container/ThemeSheetWriter'], 

+	function(mTextTheme, ThemeSheetWriter) {

 

 		function StyleSet(){

 		

@@ -42,7 +42,7 @@
 		function ThemeData(){

 		

 			this.styles = [];

-

+			

 			var orion = new StyleSet();

 			orion.name = 'Orion';

 			orion.navbar = '#333';

@@ -178,7 +178,7 @@
 		

 		

 		function getThemeStorageInfo(){

-			var themeInfo = { storage:'/themes', styleset:'styles', defaultTheme:'orion', selectedKey: 'selected'  }; 

+			var themeInfo = { storage:'/themes', styleset:'styles', defaultTheme:'Orion', selectedKey: 'selected'  }; 

 			return themeInfo;

 		}

 

@@ -265,13 +265,9 @@
 		

 		function processSettings( settings ){

 			var sheetMaker = new ThemeSheetWriter.ThemeSheetWriter();

-			var cssdata = sheetMaker.getSheet( settings );

-			

-			var stylesheet = document.createElement("STYLE");

-			stylesheet.appendChild(document.createTextNode(cssdata));

-			

-			var head = document.getElementsByTagName("HEAD")[0] || document.documentElement;

-			head.appendChild(stylesheet);

+			var themeClass = "orionTheme";

+			var theme = new mTextTheme.TextTheme.getTheme(themeClass);

+			theme.setThemeClass(themeClass, sheetMaker.getSheet( settings ));

 		}

 		

 		ThemeData.prototype.processSettings = processSettings;

diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/MiniThemeChooser.js b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/MiniThemeChooser.js
index 19acfaf..8f6bb4c11 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/MiniThemeChooser.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/MiniThemeChooser.js
@@ -11,20 +11,11 @@
 /*global orion window console define localStorage*/

 /*jslint browser:true*/

 

-define(['i18n!orion/settings/nls/messages', 'require','orion/widgets/themes/editor/ThemeData', 'orion/editor/textTheme', 'orion/widgets/input/Select'], 

-	function(messages, require, ThemeData, mTextTheme, Select ) {

+define(['i18n!orion/settings/nls/messages', 'orion/widgets/input/Select'], 

+	function(messages, Select ) {

 

 		function MiniThemeChooser(preferences){			

 			this.preferences = preferences;

-			this.themeData = new ThemeData.ThemeData();

-			this.initializeStorage();

-			var miniChooser = this;

-			//TODO: Need an abstract class that both setup.js and MiniThemeChooser.js can use to change the settings

-			var storageKey = preferences.listenForChangedSettings(function(e) {

-				if (e.key === storageKey) {

-					miniChooser.selectTheme();

-				}

-			});

 		}

 		

 		MiniThemeChooser.prototype.template =	'<div id="themeContainer">' +

@@ -77,234 +68,74 @@
 		function appendTo( node ){

 		

 			this.container = node;

-			node.innerHTML = this.template;		

-			this.addFontSizePicker();

-			this.addThemePicker();		

+			node.innerHTML = this.template;

+			this.preferences.getTheme(function(themeStyles) {

+				this.addFontSizePicker(themeStyles);

+				this.addThemePicker(themeStyles);		

+			}.bind(this));

 		}

 		

 		MiniThemeChooser.prototype.appendTo = appendTo;	

 		

-		function selectTheme( name ){

-			

-			var themeInfo = this.themeData.getThemeStorageInfo();

-			var themeData = this.themeData;

-			var settings;

-			

-			var miniChooser = this;

-		

-			this.preferences.getPreferences(themeInfo.storage, 2).then(function(prefs){ //$NON-NLS-0$

-				var currentTheme = prefs.get( 'selected' );

-				

-				if( !currentTheme && !name ){	

-					name = themeInfo.defaultTheme;

-					var styleset = themeData.getStyles();

-					prefs.put( themeInfo.styleset, JSON.stringify(styleset) );

-				}

-				

-				if( currentTheme ){

-					currentTheme = JSON.parse ( currentTheme );

-				} else {

-					currentTheme = {};

-					currentTheme[themeInfo.selectedKey] = name;

-				}

-				

-				if( currentTheme && !name ) {

-					name = currentTheme[themeInfo.selectedKey];

-				}

-				

-				if( name ){

-				

-					currentTheme[themeInfo.selectedKey] = name;

-				

-					var styles = prefs.get(	themeInfo.styleset );

-					

-					if( styles ){	

-						styles = JSON.parse( styles ); 

-						

-						for( var s in styles ){

-						

-							if( styles[s].name === name ){

-								

-								settings = styles[s];

-								break;

-							}			

-						}

-					}

-					prefs.put( 'selected', JSON.stringify(currentTheme) );

-					

-					miniChooser.setThemeData( settings );

-				}		

-			} );

+		function selectTheme( name ) {

+			this.preferences.setTheme(name);

 		}

 		

 		MiniThemeChooser.prototype.selectTheme = selectTheme;

-		

-		function setThemeData( settings ){

-			var themeClass = "editorTheme";

-			var theme = mTextTheme.TextTheme.getTheme();

-			theme.setThemeClass(themeClass, theme.buildStyleSheet(themeClass, settings));

-		}

-		

-		MiniThemeChooser.prototype.setThemeData = setThemeData;

-		

-		function initializeStorage(){

-			this.selectTheme();

-		}

-		

-		MiniThemeChooser.prototype.initializeStorage = initializeStorage;

-		

-		function selectFontSize( size ){

-		

-			var themeInfo = this.themeData.getThemeStorageInfo();

-			

-			var miniChooser = this;

-		

-			this.preferences.getPreferences(themeInfo.storage, 2).then(function(prefs){

-				var styles = prefs.get( themeInfo.styleset );

-				var selection = prefs.get( 'selected' );

-				if(selection){ selection = JSON.parse( selection ); }

-				var settings;

-				

-				if( styles ){	

-					styles = JSON.parse( styles );

-					

-					for( var s = 0; s < styles.length; s++ ){

-						styles[s].fontSize = size;

-						if( styles[s].name ===  selection[themeInfo.selectedKey] ){

-							settings = styles[s];

-						}

-						

-					}

-				}

 

-				prefs.put( themeInfo.styleset , JSON.stringify(styles) );

-				

-				if( settings ){ 

-					miniChooser.setThemeData( settings );

-				}

-			});

+		function selectFontSize( size ){

+			this.preferences.setFontSize(size);

 		}

 		

 		MiniThemeChooser.prototype.selectFontSize = selectFontSize;

 		

-		function addFontSizePicker(){

-		

-			var miniChooser = this;

+		function addFontSizePicker( themeStyles ){

+			this.fontSize = themeStyles.style.fontSize;

 			

-			var currentSize = '10pt';

+			var options = [];

+			for( var size = 8; size < 19; size++ ){

 			

-			var themeInfo = this.themeData.getThemeStorageInfo();

-			

-			this.preferences.getPreferences(themeInfo.storage, 2).then(function(prefs){

-				var styles = prefs.get( themeInfo.styleset );

-				var selection = prefs.get( 'selected' );

-				if(selection){ selection = JSON.parse( selection ); }

-				if( styles ){	

-					styles = JSON.parse( styles );

-					for( var s = 0; s < styles.length; s++ ){

-						if( styles[s].name ===  selection[themeInfo.selectedKey] ){

-							currentSize = styles[s].fontSize;

-							break;

-						}

-					}

+				var set = {

+					value: size + 'pt',

+					label: size + 'pt'

+				};

+				

+				if( set.label === this.fontSize ){

+					set.selected = true;

 				}

 				

-				var picker = document.getElementById( 'fontsizepicker' );

+				options.push(set);

+			}	

 			

-				var options = [];

-				

-				for( var size = 8; size < 19; size++ ){

-						

-					var set = {

-						value: size + 'pt',

-						label: size + 'pt'

-					};	

-					

-					if( set.label === currentSize ){ set.selected = true; }

-					

-					this.fontSize = currentSize;

-					

-					options.push(set);

-				}	

-				

-				this.sizeSelect = new Select( { options: options }, picker );

-				this.sizeSelect.setStorageItem = miniChooser.selectFontSize.bind(miniChooser);

-				this.sizeSelect.show();

-			});

+			var picker = document.getElementById( 'fontsizepicker' );

+			this.sizeSelect = new Select( { options: options }, picker );

+			this.sizeSelect.setStorageItem = this.selectFontSize.bind(this);

+			this.sizeSelect.show();

 		}

 		

 		MiniThemeChooser.prototype.addFontSizePicker = addFontSizePicker;

 		

-		

-		function setUpPicker(prefs){ //$NON-NLS-0$

-		

-			var themeInfo = this.themeData.getThemeStorageInfo();

-				

+		function addThemePicker( themeStyles ){

+			var styles = themeStyles.styles;

 			var options = [];

+			for( var theme= 0; theme < styles.length; theme++ ){

 			

-			var chooser = this;

-

-				var selection = prefs.get( 'selected' );

+				var set = {

+					value: styles[theme].name,

+					label: styles[theme].name

+				};	

 				

-				if(selection){ selection = JSON.parse( selection ); }

-				

-				var styles = prefs.get( themeInfo.styleset );

-				

-				if(styles){ styles = JSON.parse( styles ); }

-

-				if(!styles){

-				

-					/* If we're in this condition, then the themes are not in local storage yet.

-					   Going to make sure */

-				

-					styles = chooser.styleset; 

+				if( styles[theme].name === themeStyles.style.name ){

+					set.selected = true;

 				}

 				

-				if(!selection) {

-					selection = {};	

-					selection[themeInfo.selectedKey] = themeInfo.defaultTheme;

-				}

-			

-				if( styles ){

-				

-					for( var theme= 0; theme < styles.length; theme++ ){

-					

-						var set = {

-							value: styles[theme].name,

-							label: styles[theme].name

-						};	

-						

-						if( selection ){	

-							if( styles[theme].name === selection[themeInfo.selectedKey] ){

-								set.selected = true;

-							}

-						}

-						

-						options.push(set);

-						

-						chooser.styles = styles;

-					}	

-				}

-			

-				var picker = document.getElementById( 'themepicker' );

-				

-				this.themeSelect = new Select( { options: options }, picker );

-				this.themeSelect.setStorageItem = chooser.selectTheme.bind(chooser); 

-				this.themeSelect.show();

-			}

+				options.push(set);

+			}	

 		

-		MiniThemeChooser.prototype.setUpPicker = setUpPicker;

-				

-		function addThemePicker(){

-			

-			var themeInfo = this.themeData.getThemeStorageInfo();

-			

-			/* Check to see if the Orion theme is in the themes preferences ... if it is, 

-				   then we don't need to populate again, otherwise we do need to populate. */

-				   

-			var chooser = this;

-			

-			this.preferences.getPreferences(themeInfo.storage, 2).then( chooser.setUpPicker.bind(chooser) );	

+			var picker = document.getElementById( 'themepicker' );

+			this.themeSelect = new Select( { options: options }, picker );

+			this.themeSelect.setStorageItem = this.selectTheme.bind(this);

+			this.themeSelect.show();

 		}

 		

 		MiniThemeChooser.prototype.addThemePicker = addThemePicker;

diff --git a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/ThemeData.js b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/ThemeData.js
index 8d37015..8a9f9d3 100644
--- a/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/ThemeData.js
+++ b/bundles/org.eclipse.orion.client.ui/web/orion/widgets/themes/editor/ThemeData.js
@@ -11,8 +11,8 @@
 /*global widgets orion window console define localStorage ActiveXObject DOMParser*/

 /*jslint browser:true*/

 

-define([], 

-	function() {

+define(['orion/editor/textTheme'], 

+	function(mTextTheme) {

 	

 		/* Synchronizing colors and styles for HTML, CSS and JS files like this ...

 	

@@ -54,7 +54,7 @@
 		StyleSet.prototype.attribute = 'cadetBlue';

 		StyleSet.prototypefontSize = '10pt';

 

-			function ThemeData() {

+		function ThemeData() {

 

 		this.styles = [];

 

@@ -703,7 +703,9 @@
 		ThemeData.prototype.importTheme = importTheme;

 		

 		function processSettings( settings, preferences ){

-

+			var themeClass = "editorTheme";

+			var theme = mTextTheme.TextTheme.getTheme();

+			theme.setThemeClass(themeClass, theme.buildStyleSheet(themeClass, settings));

 		}

 

 		ThemeData.prototype.processSettings = processSettings;

diff --git a/modules/orionode/lib/orionode.client/orion/widgets/settings/SettingsContainer.js b/modules/orionode/lib/orionode.client/orion/widgets/settings/SettingsContainer.js
index 96573f8..1167d52 100644
--- a/modules/orionode/lib/orionode.client/orion/widgets/settings/SettingsContainer.js
+++ b/modules/orionode/lib/orionode.client/orion/widgets/settings/SettingsContainer.js
@@ -18,13 +18,14 @@
 		'orion/PageUtil', 'orion/webui/littlelib', 'orion/objects', 'orion/URITemplate', 
 		'orion/widgets/themes/ThemeBuilder', 
 		'orion/settings/ui/PluginSettings', 
+		'orion/widgets/themes/ThemePreferences', 
 		'orion/widgets/themes/editor/ThemeData', 
 		'orion/widgets/themes/container/ThemeData', 
 		'orion/widgets/settings/SplitSelectionLayout',
 		'orion/widgets/plugin/PluginList',
 		'orion/widgets/settings/UserSettings'
 		], function(messages, require, mGlobalCommands, PageUtil, lib, objects, URITemplate, 
-			ThemeBuilder, SettingsList, editorThemeData, containerThemeData, SplitSelectionLayout, PluginList, UserSettings) {
+			ThemeBuilder, SettingsList, mThemePreferences, editorThemeData, containerThemeData, SplitSelectionLayout, PluginList, UserSettings) {
 
 	/**
 	 * @param {Object} options
@@ -122,8 +123,9 @@
 			}
 			
 			var containerTheme = new containerThemeData.ThemeData();
+			var themePreferences = new mThemePreferences.ThemePreferences(this.preferences, containerTheme);
 		
-			this.themeWidget = new ThemeBuilder({ commandService: this.commandService, preferences: this.preferences, themeData: containerTheme });
+			this.themeWidget = new ThemeBuilder({ commandService: this.commandService, preferences: themePreferences, themeData: containerTheme });
 			
 			lib.empty(this.table);