Clone in a terminal:
Commit 295fbc2
Johan Mattsson - 2015-03-10T05:35:17+00:00
295fbc2f0afcef8a36eab972222986c7f79704c4johan.mattsson.m@gmail.com

Customizable color theme

Changed files (53)

Diff

diff --git a/libbirdfont/BackgroundImage.vala b/libbirdfont/BackgroundImage.valaindex 779f1b9..910ad68 100644--- a/libbirdfont/BackgroundImage.vala+++ b/libbirdfont/BackgroundImage.vala@@ -429,7 +429,7 @@ public class BackgroundImage { 		ct = new Context (st); 		ct.save (); -		ct.set_source_rgba (1, 1, 1, 1);+		Theme.color (ct, "Background 1"); 		ct.rectangle (0, 0, allocation.width, allocation.height); 		ct.fill (); @@ -477,7 +477,7 @@ public class BackgroundImage { 		wc = get_margin_width (); 		hc = get_margin_height (); 		-		cg.set_source_rgba (1, 1, 1, 1);+		Theme.color (cg, "Background 1"); 		cg.rectangle (0, 0, size_margin, size_margin); 		cg.fill (); 		@@ -502,7 +502,7 @@ public class BackgroundImage { 	 		c.save (); -		c.set_source_rgba (1, 1, 1, 1);+		Theme.color (c, "Background 1"); 		c.rectangle (0, 0, size_margin, size_margin); 		c.fill (); 			@@ -589,7 +589,7 @@ public class BackgroundImage { 		double x, y; 		cr.save (); 		-		cr.set_source_rgba (1, 0, 0.3, 1);+		Theme.color (cr, "Background 3");  		x = img_middle_x - (img_scale_x * get_img ().get_width () / 2); 		y = img_middle_y - (img_scale_y * get_img ().get_height () / 2);@@ -611,9 +611,9 @@ public class BackgroundImage { 		 		cr.scale (g.view_zoom, g.view_zoom); 		-		if (selected_handle == 2) cr.set_source_rgba (1, 0, 0.3, 1);-		else if (active_handle == 2) cr.set_source_rgba (0, 0, 0.3, 1);-		else cr.set_source_rgba (0.7, 0.7, 0.8, 1);+		if (selected_handle == 2) Theme.color (cr, "Highlighted 1");+		else if (active_handle == 2) Theme.color (cr, "Background 4");+		else Theme.color (cr, "Background 3");  		x = img_offset_x - g.view_offset_x + (size_margin / 2) * img_scale_x; 		y = img_offset_y - g.view_offset_y + (size_margin / 2) * img_scale_y;@@ -647,9 +647,9 @@ public class BackgroundImage { 		cr.save (); 		cr.set_line_width (ivz); 		-		if (selected_handle == 1) cr.set_source_rgba (1, 0, 0.3, 1);-		else if (active_handle == 1) cr.set_source_rgba (0, 0, 0.3, 1);-		else cr.set_source_rgba (0.7, 0.7, 0.8, 1);	+		if (selected_handle == 1) Theme.color (cr, "Highlighted 1");+		else if (active_handle == 1) Theme.color (cr, "Background 4");+		else Theme.color (cr, "Background 3");  		size = (8) * s; 		@@ -712,7 +712,7 @@ public class BackgroundImage { 		c = new Context (s); 	 		c.save ();-		c.set_source_rgba (1, 1, 1, 1);+		Theme.color (c, "Background 1"); 		c.rectangle (0, 0, scaled_width, scaled_width); 		c.fill (); diff --git a/libbirdfont/BackgroundSelectionTool.vala b/libbirdfont/BackgroundSelectionTool.valaindex 69fd4eb..4d42b9d 100644--- a/libbirdfont/BackgroundSelectionTool.vala+++ b/libbirdfont/BackgroundSelectionTool.vala@@ -68,7 +68,6 @@ public class BackgroundSelectionTool : CutBackgroundTool { 				if (bs.assigned_glyph != null) { 					if (label.has_character ((!) bs.assigned_glyph)) { 						font_height = 18;-						cr.set_source_rgba (1, 1, 1, 1); 						label.set_text ((!) bs.assigned_glyph); 						label.set_font_size (font_height); 						tx = x  + w - label.get_width () / 2.0;diff --git a/libbirdfont/BirdFont.vala b/libbirdfont/BirdFont.valaindex aa73bf2..6926c8d 100644--- a/libbirdfont/BirdFont.vala+++ b/libbirdfont/BirdFont.vala@@ -428,6 +428,12 @@ public class BirdFont {  		Preferences.load (); 		+		// FIXME: DELETE+		Theme.load_theme ();+		save_default_colors ();++		Theme.load_theme ();+		 		current_font = new Font (); 		current_font.set_name (""); 		current_font.initialised = false;@@ -478,7 +484,7 @@ public class BirdFont { 		} 		 		Preferences.set_last_file (get_current_font ().get_path ());-		+ 		DefaultCharacterSet.create_default_character_sets (); 		DefaultCharacterSet.get_characters_for_prefered_language (); @@ -489,6 +495,51 @@ public class BirdFont { 		} 	} +	void save_default_colors () {+		Theme.save_color ("Background 1", 1, 1, 1, 1);+		Theme.save_color ("Background 2", 101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+		Theme.save_color ("Background 3", 38 / 255.0, 39 / 255.0, 43 / 255.0, 1);+		Theme.save_color ("Background 4", 51 / 255.0, 54 / 255.0, 59 / 255.0, 1);+		Theme.save_color ("Background 5", 0.3, 0.3, 0.3, 1);+		Theme.save_color ("Background 6", 224/255.0, 224/255.0, 224/255.0, 1);+		Theme.save_color ("Background 7", 56 / 255.0, 59 / 255.0, 65 / 255.0, 1);+		Theme.save_color ("Background 7", 55/255.0, 55/255.0, 55/255.0, 1);+		Theme.save_color ("Background 9", 72/255.0, 72/255.0, 72/255.0, 1);+		+		Theme.save_color ("Foreground 1", 0, 0, 0, 1);+		Theme.save_color ("Foreground 2", 101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+		Theme.save_color ("Foreground 3", 26 / 255.0, 30 / 255.0, 32 / 255.0, 1);+		Theme.save_color ("Foreground 4", 40 / 255.0, 57 / 255.0, 65 / 255.0, 1);+		Theme.save_color ("Foreground 5", 70 / 255.0, 77 / 255.0, 83 / 255.0, 1);+		+		Theme.save_color ("Highlighted 1", 234 / 255.0, 77 / 255.0, 26 / 255.0, 1);+		+		Theme.save_color ("Highlighted Guide", 0, 0, 0.3, 1);+		Theme.save_color ("Guide 1", 0.7, 0.7, 0.8, 1);+		Theme.save_color ("Guide 2", 0.7, 0, 0, 0.5);+		Theme.save_color ("Guide 3", 120 / 255.0, 68 / 255.0, 120 / 255.0, 120 / 255.0);+		+		Theme.save_color ("Grid",0.2, 0.6, 0.2, 0.2);+		+		Theme.save_color ("Background Glyph", 0.2, 0.2, 0.2, 0.5);+		+		N_("Background 1");+		N_("Background 2");+		N_("Background 3");+		N_("Background 4");+		N_("Background 5");+		N_("Background 6");+		N_("Background 7");+		N_("Background 8");+		N_("Background 9");+		+		N_("Foreground 1");+		N_("Foreground 2");+		N_("Foreground 3");+		+		N_("Highlighted 1");+	}+ 	public static void set_bundle_path (string path) { 		bundle_path = path;	 	}diff --git a/libbirdfont/BirdFontFile.vala b/libbirdfont/BirdFontFile.valaindex 6e6afe6..37c8c62 100644--- a/libbirdfont/BirdFontFile.vala+++ b/libbirdfont/BirdFontFile.vala@@ -132,8 +132,6 @@ class BirdFontFile : GLib.Object { 				} catch (GLib.Error e) { 					warning (e.message); 				}-					-				TooltipArea.show_text (t_("Saving")); 			}); 			 			os.put_string ("\n");@@ -168,8 +166,6 @@ class BirdFontFile : GLib.Object { 					warning (@"Failed to save $path \n"); 					warning (@"$(ef.message) \n"); 				}-					-				TooltipArea.show_text (t_("Saving")); 			}); 			 			os.put_string ("\n");@@ -312,8 +308,6 @@ class BirdFontFile : GLib.Object { 				} catch (GLib.Error e) { 					warning (@"$(e.message) \n"); 				}-				-				TooltipArea.show_text (t_("Saving")); 			}); 	} 	@@ -726,8 +720,7 @@ class BirdFontFile : GLib.Object { 				parse_images (t); 			} 		}--		TooltipArea.show_text ("");+		 		return true; 	} 		diff --git a/libbirdfont/Button.vala b/libbirdfont/Button.valaindex 62d7d76..d87ef20 100644--- a/libbirdfont/Button.vala+++ b/libbirdfont/Button.vala@@ -27,19 +27,19 @@ public class Button : Widget { 	public Button (string label) { 		font_size =  17 * MainWindow.units; 		this.label = new Text (label, font_size);-		this.label.set_source_rgba (1, 1, 1, 1);+		Theme.text_color (this.label, "Background 1"); 		padding = 15 * MainWindow.units; 	}  	public override void draw (Context cr) {	 		cr.save ();-		cr.set_source_rgba (51 / 255.0, 54 / 255.0, 59 / 255.0, 1);+		Theme.color (cr, "Background 4"); 		draw_rounded_rectangle (cr, widget_x, widget_y, get_width (), padding, padding); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0, 1);+		Theme.color (cr, "Foreground 1"); 		cr.set_line_width (1); 		draw_rounded_rectangle (cr, widget_x, widget_y, get_width (), padding, padding); 		cr.stroke ();diff --git a/libbirdfont/CharDatabase.vala b/libbirdfont/CharDatabase.valaindex ab3f27e..cbfce9c 100644--- a/libbirdfont/CharDatabase.vala+++ b/libbirdfont/CharDatabase.vala@@ -36,10 +36,6 @@ public class CharDatabase { 		GlyphRange ucd_result = new GlyphRange (); 		unichar c; 		-		if (!database_is_loaded) {-			show_loading_message ();-		}- 		return_val_if_fail (!is_null (index), result);		 		return_val_if_fail (result.get_length () == 0, result); 		@@ -130,15 +126,7 @@ public class CharDatabase { 		return description;		 	} 	-	public static void show_loading_message () {-		TooltipArea.show_text (t_("Loading the unicode character database") + " ...");-	}-	 	public static void get_full_unicode (GlyphRange glyph_range) {-		if (!database_is_loaded) {-			show_loading_message ();-		}-		 		try { 			if (!is_null (full_unicode_range)) { 				glyph_range.parse_ranges (full_unicode_range.get_all_ranges ());diff --git a/libbirdfont/CharDatabaseParser.vala b/libbirdfont/CharDatabaseParser.valaindex e4667e0..7de6584 100644--- a/libbirdfont/CharDatabaseParser.vala+++ b/libbirdfont/CharDatabaseParser.vala@@ -147,7 +147,6 @@ public class CharDatabaseParser : GLib.Object { 		IdleSource idle = new IdleSource (); 		idle.set_callback (() => { 			CharDatabase.full_unicode_range = utf8;-			CharDatabase.show_loading_message (); 			CharDatabase.database_is_loaded = true; 			return false; 		});diff --git a/libbirdfont/CheckBox.vala b/libbirdfont/CheckBox.valaindex 276fc46..e76715f 100644--- a/libbirdfont/CheckBox.vala+++ b/libbirdfont/CheckBox.vala@@ -54,14 +54,14 @@ public class CheckBox : Widget { 		double center_y = (get_height () - (h + 2 * padding)) / 2.0 + padding;  		cr.save ();-		cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);		+		Theme.color (cr, "Background 2");	 		draw_rounded_rectangle (cr, widget_x, widget_y + center_y, w, h - padding, padding); 		cr.fill (); 		cr.restore (); 		 		cr.save (); 		cr.set_line_width (1);-		cr.set_source_rgba (0, 0, 0, 1);		+		Theme.color (cr, "Foreground 1"); 		draw_rounded_rectangle (cr, widget_x, widget_y + center_y, w, h - padding, padding); 		cr.stroke (); 		cr.restore ();@@ -69,7 +69,7 @@ public class CheckBox : Widget { 		if (checked) { 			cr.save (); 			-			cr.set_source_rgba (0, 0, 0, 1);+			Theme.color (cr, "Foreground 1"); 			cr.set_line_width (1); 			 			cr.move_to (widget_x + d, widget_y + d + center_y);diff --git a/libbirdfont/CutBackgroundTool.vala b/libbirdfont/CutBackgroundTool.valaindex 4182dfa..4980ee7 100644--- a/libbirdfont/CutBackgroundTool.vala+++ b/libbirdfont/CutBackgroundTool.vala@@ -94,7 +94,7 @@ public class CutBackgroundTool : Tool { 				// draw a border around the selection 				cr.save (); 				cr.set_line_width (2.0);-				cr.set_source_rgba (0, 0, 0, 0.3);+				Theme.color_opacity (cr, "Foreground 1", 0.3); 				cr.rectangle (fmin (x1, x2), fmin (y1, y2), fabs (x1 - x2), fabs (y1 - y2)); 				cr.stroke (); 				cr.restore ();@@ -102,7 +102,7 @@ public class CutBackgroundTool : Tool { 				// make the area outside of the selection grey 				cr.save (); 				cr.set_line_width (0);-				cr.set_source_rgba (0, 0, 0, 0.075);+				Theme.color_opacity (cr, "Foreground 1", 0.075); 				cr.rectangle (0, 0, glyph.allocation.width, fmin (y1, y2)); 				cr.rectangle (0, fmin (y1, y2), fmin (x1, x2), fabs (y1 - y2)); 				cr.rectangle (0, fmin (y1, y2) + fabs (y1 - y2), glyph.allocation.width, glyph.allocation.height - fabs (y1 - y2));@@ -170,7 +170,7 @@ public class CutBackgroundTool : Tool { 		wc = bg.get_margin_width (); 		hc = bg.get_margin_height (); 		-		cg.set_source_rgba (1, 1, 1, 1);+		Theme.color (cg, "Background 1"); 		cg.rectangle (0, 0, bg.size_margin, bg.size_margin); 		cg.fill (); @@ -203,7 +203,7 @@ public class CutBackgroundTool : Tool { 		sr = new Surface.similar (sg, img.get_content (), (int) (w / bg.img_scale_x), (int) (h / bg.img_scale_y)); 		cr = new Context (sr); -		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (0, 0, w, h); 		cr.fill (); diff --git a/libbirdfont/DescriptionDisplay.vala b/libbirdfont/DescriptionDisplay.valaindex adae374..997ac16 100644--- a/libbirdfont/DescriptionDisplay.vala+++ b/libbirdfont/DescriptionDisplay.vala@@ -181,7 +181,9 @@ public class DescriptionDisplay : FontDisplay { 		cr.save (); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.set_line_width (0);-		cr.set_source_rgba (51 / 255.0, 54 / 255.0, 59 / 255.0, 1);+		+		Theme.color (cr, "Background 4");+ 		cr.fill (); 		cr.stroke (); 		cr.restore ();@@ -190,7 +192,7 @@ public class DescriptionDisplay : FontDisplay { 			if (w.is_on_screen ()) {			 				if (w is Text) { 					cr.save ();-					cr.set_source_rgba (0, 0, 0, 1);+					Theme.color (cr, "Foreground 1"); 					w.draw (cr); 					cr.restore (); 				} else {diff --git a/libbirdfont/EmptyTab.vala b/libbirdfont/EmptyTab.valaindex caae8ef..a81247d 100644--- a/libbirdfont/EmptyTab.vala+++ b/libbirdfont/EmptyTab.vala@@ -36,7 +36,7 @@ public class EmptyTab : FontDisplay {  	public override void draw (WidgetAllocation allocation, Context cr) { 		cr.save ();-		cr.set_source_rgba (242/255.0, 241/255.0, 240/255.0, 1);+		Theme.color (cr, "Background 9"); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore ();diff --git a/libbirdfont/Expander.vala b/libbirdfont/Expander.valaindex 2a4bb77..a337e69 100644--- a/libbirdfont/Expander.vala+++ b/libbirdfont/Expander.vala@@ -232,13 +232,13 @@ public class Expander : GLib.Object { 			if (headline != null) { 				title = new Text (); 				title.set_text ((!) headline);-				title.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+				Theme.text_color (title, "Foreground 2"); 				title.set_font_size (17 * Toolbox.get_scale ()); 				title.draw_at_baseline (cr, x, yt + HEADLINE_MARGIN + 13  * Toolbox.get_scale ());-			} else if (draw_separator) {		+			} else if (draw_separator) {	 				cr.save (); 				cr.set_line_width (0.5);-				cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+				Theme.color (cr, "Foreground 2"); 				cr.move_to (x, yt); 				cr.line_to (wd - w - x + 6, yt);	 				cr.stroke ();@@ -248,7 +248,8 @@ public class Expander : GLib.Object { 				cr.save (); 				cr.new_path (); 				cr.set_line_width (1);-				cr.set_source_rgba (0, 0, 0, opacity);+				+				Theme.color_opacity (cr, "Foreground 2", opacity); 				 				cr.move_to (x - iw2 + 3, yt - ih2 - 0.7 + 1); 				cr.line_to (x + iw2 + 3, yt - ih2 - 0.7 + 1);diff --git a/libbirdfont/ExportCallback.vala b/libbirdfont/ExportCallback.valaindex b6628e9..eec6851 100644--- a/libbirdfont/ExportCallback.vala+++ b/libbirdfont/ExportCallback.vala@@ -43,7 +43,6 @@ public class ExportCallback : GLib.Object { 	public static void export_fonts () { 		ExportTool.export_ttf_font (); 		ExportTool.export_svg_font ();-		TooltipArea.show_text (t_("Three font files have been created."));	 	} } diff --git a/libbirdfont/ExportTool.vala b/libbirdfont/ExportTool.valaindex 7d93258..024d31b 100644--- a/libbirdfont/ExportTool.vala+++ b/libbirdfont/ExportTool.vala@@ -401,9 +401,7 @@ os.put_string ( 			if (eot_file.query_exists ()) { 				eot_file.delete (); 			}-			-			TooltipArea.show_text (t_("Writing TTF and EOT files."));-			+						 			write_ttf ((!) ttf_file.get_path ()); 			write_eot ((!) ttf_file.get_path (), (!) eot_file.get_path ()); 		} catch (Error e) {@@ -416,7 +414,6 @@ os.put_string (  	public static bool export_svg_font () { 		Font font = BirdFont.get_current_font ();-		TooltipArea.show_text (t_("Writing SVG file.")); 		return export_svg_font_path (font.get_folder ()); 	} 		@@ -439,7 +436,6 @@ os.put_string ( 			fo.close (); 		} catch (Error e) { 			critical (@"$(e.message)");-			TooltipArea.show_text (e.message); 			return false; 		} 		diff --git a/libbirdfont/FileDialogTab.vala b/libbirdfont/FileDialogTab.valaindex 567a2ee..d356314 100644--- a/libbirdfont/FileDialogTab.vala+++ b/libbirdfont/FileDialogTab.vala@@ -150,13 +150,13 @@ public class FileDialogTab : FontDisplay { 		visible_rows = (int) (allocation.height / 18.0); 		 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 4"); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0.3, 0.3, 0.3, 1);+		Theme.color (cr, "Background 5"); 		cr.set_font_size (12);  		foreach (string file in directories) {@@ -184,13 +184,13 @@ public class FileDialogTab : FontDisplay { 		if (color) { 			if (dark) { 				cr.save ();-				cr.set_source_rgba (55/255.0, 55/255.0, 55/255.0, 1);+				Theme.color (cr, "Background 8"); 				cr.rectangle (0, y - 14 * MainWindow.units, allocation.width, 18 * MainWindow.units); 				cr.fill (); 				cr.restore (); 			} else { 				cr.save ();-				cr.set_source_rgba (224/255.0, 224/255.0, 224/255.0, 1);+				Theme.color (cr, "Background 6"); 				cr.rectangle (0, y - 14 * MainWindow.units, allocation.width, 18 * MainWindow.units); 				cr.fill (); 				cr.restore ();@@ -198,7 +198,7 @@ public class FileDialogTab : FontDisplay { 		} else { 			if (dark) { 				cr.save ();-				cr.set_source_rgba (72/255.0, 72/255.0, 72/255.0, 1);+				Theme.color (cr, "Background 9"); 				cr.rectangle (0, y - 14 * MainWindow.units, allocation.width, 18 * MainWindow.units); 				cr.fill (); 				cr.restore ();@@ -207,7 +207,7 @@ public class FileDialogTab : FontDisplay { 		 		cr.save (); 		if (dark) {-			cr.set_source_rgba (255/255.0, 255/255.0, 255/255.0, 1);+			Theme.color (cr, "Background 1"); 		} 		cr.move_to (60, y); 		cr.set_font_size (12 * MainWindow.units);diff --git a/libbirdfont/FileTab.vala b/libbirdfont/FileTab.valaindex cf09cdc..af9c78b 100644--- a/libbirdfont/FileTab.vala+++ b/libbirdfont/FileTab.vala@@ -238,14 +238,14 @@ public class FileTab : FontDisplay { 		visible_rows = (int) (allocation.height / row_height); 		 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore ();  		if (recent_fonts.size == 0 && !has_backup ()) { 			cr.save ();-			cr.set_source_rgba (0.3, 0.3, 0.3, 1);+			Theme.color (cr, "Background 5"); 			cr.set_font_size (18 * MainWindow.units); 			cr.move_to (50 * MainWindow.units, top - 9 * MainWindow.units); 			cr.show_text (t_("No fonts created yet."));@@ -256,7 +256,7 @@ public class FileTab : FontDisplay { 		 		if (scroll == 0 && recent_fonts.size > 0) { 			cr.save ();-			cr.set_source_rgba (0.3, 0.3, 0.3, 1);+			Theme.color (cr, "Background 5"); 			cr.set_font_size (18 * MainWindow.units); 			cr.move_to (50 * MainWindow.units, top - 9 * MainWindow.units); 			cr.show_text (t_("Recent files"));@@ -264,7 +264,7 @@ public class FileTab : FontDisplay { 		} 		 		cr.save ();-		cr.set_source_rgba (0.3, 0.3, 0.3, 1);+		Theme.color (cr, "Background 5"); 		cr.set_font_size (12 * MainWindow.units);  		foreach (Font font in recent_fonts) {@@ -280,7 +280,7 @@ public class FileTab : FontDisplay { 			 			if (s >= scroll) { 				cr.save ();-				cr.set_source_rgba (0.3, 0.3, 0.3, 1);+				Theme.color (cr, "Background 5"); 				cr.set_font_size (18 * MainWindow.units); 				cr.move_to (50 * MainWindow.units, y + 2 * row_height - 9 * MainWindow.units); 				cr.show_text (t_("Backup"));diff --git a/libbirdfont/Font.vala b/libbirdfont/Font.valaindex 9d8b297..4493703 100644--- a/libbirdfont/Font.vala+++ b/libbirdfont/Font.vala@@ -648,7 +648,6 @@ public class Font : GLib.Object {  		if (read_only) { 			warning (@"$path is write protected.");-			TooltipArea.show_text (t_("The file is write protected.")); 			return;			 		} 				diff --git a/libbirdfont/FontName.vala b/libbirdfont/FontName.valaindex 0ac2945..3e42b26 100644--- a/libbirdfont/FontName.vala+++ b/libbirdfont/FontName.vala@@ -50,7 +50,7 @@ public class FontName : Tool { 			text_height *= max_width / extent; 		} 		-		font_name.set_source_rgba (234 / 255.0, 77 / 255.0, 26 / 255.0, 1);+		Theme.text_color (font_name, "Highlighted 1"); 		font_name.set_font_size (text_height); 		font_name.draw_at_baseline (cr, x, y + 13 * Toolbox.get_scale ()); 		cr.restore ();diff --git a/libbirdfont/Glyph.vala b/libbirdfont/Glyph.valaindex f243d52..bae1811 100644--- a/libbirdfont/Glyph.vala+++ b/libbirdfont/Glyph.vala@@ -404,7 +404,7 @@ public class Glyph : FontDisplay { 		 		double bgt = BirdFont.get_current_font ().top_limit; 		Line top_margin_line = new Line ("top margin", bgt, false);-		top_margin_line.set_color (0.7, 0, 0, 0.5);+		top_margin_line.set_color_theme ("Guide 2"); 		top_margin_line.position_updated.connect ((pos) => { 			BirdFont.get_current_font ().top_limit = pos; 		});@@ -418,7 +418,7 @@ public class Glyph : FontDisplay { 		 		double xhp = BirdFont.get_current_font ().xheight_position; 		Line xheight_line = new Line ("x-height", xhp, false);-		xheight_line.set_color (120 / 255.0, 68 / 255.0, 120 / 255.0, 120 / 255.0);+		xheight_line.set_color_theme ("Guide 3"); 		xheight_line.dashed = true; 		xheight_line.position_updated.connect ((pos) => {				 				Font f = BirdFont.get_current_font ();@@ -434,14 +434,13 @@ public class Glyph : FontDisplay { 		 		double bp = BirdFont.get_current_font ().bottom_position; 		Line bottom_line = new Line ("bottom", bp, false);-		bottom_line.set_color (33 / 255.0, 68 / 255.0, 120 / 255.0, 166 / 255.0); 		bottom_line.position_updated.connect ((pos) => { 				BirdFont.get_current_font ().bottom_position = pos; 			});  		double bgb = BirdFont.get_current_font ().bottom_limit; 		Line bottom_margin_line = new Line ("bottom margin", bgb, false);-		bottom_margin_line.set_color (0.7, 0, 0, 0.5);+		bottom_margin_line.set_color_theme ("Guide 2"); 		bottom_margin_line.position_updated.connect ((pos) => { 			BirdFont.get_current_font ().bottom_limit = pos; 		});@@ -1428,7 +1427,7 @@ public class Glyph : FontDisplay { 	} 	 	private void draw_coordinate (Context cr) {-		cr.set_source_rgba (0.5, 0.5, 0.5, 1);+		Theme.color (cr, "Foreground 3"); 		cr.set_font_size (12); 		cr.move_to (0, 10); 		cr.show_text (@"($motion_x, $motion_y)");@@ -1533,20 +1532,20 @@ public class Glyph : FontDisplay { 	private void draw_zoom_area(Context cr) { 		cr.save (); 		cr.set_line_width (2.0);-		cr.set_source_rgba (0, 0, 1, 0.3);+		Theme.color (cr, "Foreground 3"); 		cr.rectangle (Math.fmin (zoom_x1, zoom_x2), Math.fmin (zoom_y1, zoom_y2), Math.fabs (zoom_x1 - zoom_x2), Math.fabs (zoom_y1 - zoom_y2)); 		cr.stroke (); 		cr.restore (); 	}  	private void draw_background_color (Context cr, double opacity) {-		cr.save ();-		cr.rectangle (0, 0, allocation.width, allocation.height);-		cr.set_line_width (0);-		cr.set_source_rgba (1, 1, 1, opacity);-		cr.fill ();-		cr.stroke ();-		cr.restore ();+		if (opacity > 0) {+			cr.save ();+			cr.rectangle (0, 0, allocation.width, allocation.height);+			Theme.color (cr, "Background 1");+			cr.fill ();+			cr.restore ();+		} 	} 	 	private void draw_help_lines (Context cr) {@@ -1776,34 +1775,6 @@ public class Glyph : FontDisplay {  		redraw_area (0, 0, allocation.width, allocation.height);		 	}-	-	public ImageSurface get_thumbnail () {-		ImageSurface img;-		Context cr;-		double gx, gy;-		double x1, x2, y1, y2;-		Font font = BirdFont.get_current_font ();--		remove_empty_paths ();-		boundaries (out x1, out y1, out x2, out y2);--		if (x2 - x1 < 1 || y2 - y1 < 1) { // create an empty thumbnail -			img = new ImageSurface (Format.ARGB32, 100, 100);-		} else {-			img = new ImageSurface (Format.ARGB32, (int) (x2 - x1), (int) (y2 - y1));-		}-		-		gx = left_limit - x1;-		gy = (y2 - y1) + font.base_line + y1;-		-		cr = new Context (img);-		-		cr.save ();-		cr.set_source_rgba (0, 0, 0, 1);-		Svg.draw_svg_path (cr, get_svg_data (), gx, gy);	-		cr.restore ();-		return img;-	}  	/** Split curve in two parts and add a new point in between. 	 * @return the new point@@ -1903,7 +1874,7 @@ public class Glyph : FontDisplay { 				 				cr.save (); 				cr.scale (glyph.view_zoom, glyph.view_zoom);-				cr.set_source_rgba (0, 0, 0, 1);+				Theme.color (cr, "Foreground 1");  				Svg.draw_svg_path (cr, juxtaposed.get_svg_data (), marker_x, marker_y); 				cr.restore ();@@ -1938,7 +1909,7 @@ public class Glyph : FontDisplay { 				cr.save (); 				cr.scale (glyph.view_zoom, glyph.view_zoom); 				cr.translate (-glyph.view_offset_x, -glyph.view_offset_y);-				cr.set_source_rgba (0, 0, 0, 1);+				Theme.color (cr, "Foreground 1"); 				Svg.draw_svg_path (cr, juxtaposed.get_svg_data (), marker_x, marker_y); 				cr.restore (); 			}@@ -1972,7 +1943,8 @@ public class Glyph : FontDisplay { 			cr.save (); 			cr.scale (view_zoom, view_zoom); 			cr.translate (-view_offset_x, -view_offset_y);-			cr.set_source_rgba (0.2, 0.2, 0.2, 0.5);+			Theme.color (cr, "Background Glyph");+			 			Svg.draw_svg_path (cr, g.get_svg_data (),  				Glyph.xc () + left - (left - current_left) ,  				Glyph.yc () - baseline);diff --git a/libbirdfont/GridTool.vala b/libbirdfont/GridTool.valaindex 7d52601..c3b7cb0 100644--- a/libbirdfont/GridTool.vala+++ b/libbirdfont/GridTool.vala@@ -99,11 +99,13 @@ class GridTool : Tool { 	public static void update_lines () { 		Glyph g = MainWindow.get_current_glyph (); 		double step = size_y;+		Color color = Theme.get_color ("Grid"); 		double i; 		int max_lines = 600; 		int n; 		Line t, l, u; + 		Line baseline = g.get_line ("baseline"); 		Line bottom_margin = g.get_line ("bottom margin"); 		Line top_margin = g.get_line ("top margin");@@ -118,7 +120,7 @@ class GridTool : Tool { 		for (i = left.get_pos () - 7 * step; i <= right.get_pos () + 7 * step; i += step) {	 			l = new Line ("grid", i, Line.VERTICAL); 			l.set_moveable (false);-			l.set_color (0.2, 0.6, 0.2, 0.2);+			l.set_color (color.r, color.g, color.b, color.a); 			vertical.add (l); 			 			if (++n >= max_lines) {@@ -130,7 +132,7 @@ class GridTool : Tool { 		for (i = baseline.get_pos () - step; i >= bottom_margin.get_pos () - 7 * step; i -= step) { 			t = new Line ("grid", i, Line.HORIZONTAL); 			t.set_moveable (false);-			t.set_color (0.2, 0.6, 0.2, 0.2);+			t.set_color (color.r, color.g, color.b, color.a); 			horizontal.insert (0, t);	  			if (++n >= max_lines) {@@ -142,7 +144,7 @@ class GridTool : Tool { 		for (i = baseline.get_pos (); i <= top_margin.get_pos () + 7 * step; i += step) { 			u = new Line ("grid", i, Line.HORIZONTAL); 			u.set_moveable (false);-			u.set_color (0.2, 0.6, 0.2, 0.2);+			u.set_color (color.r, color.g, color.b, color.a); 			horizontal.add (u);	  			if (++n >= max_lines) {diff --git a/libbirdfont/Headline.vala b/libbirdfont/Headline.valaindex eb095fd..afbf5c4 100644--- a/libbirdfont/Headline.vala+++ b/libbirdfont/Headline.vala@@ -28,7 +28,7 @@ class Headline : Widget { 	 	public override void draw (Context cr) { 		cr.save ();-		cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+		Theme.color (cr, "Background 2"); 		cr.rectangle (0, widget_y, allocation.width, 40 * MainWindow.units); 		cr.fill (); 		cr.restore ();diff --git a/libbirdfont/KerningDisplay.vala b/libbirdfont/KerningDisplay.valaindex a83afe9..542f3dd 100644--- a/libbirdfont/KerningDisplay.vala+++ b/libbirdfont/KerningDisplay.vala@@ -101,7 +101,7 @@ public class KerningDisplay : FontDisplay { 		 		// bg color 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore ();@@ -166,7 +166,7 @@ public class KerningDisplay : FontDisplay { 					cr.save (); 					 					if (selected_handle == i) {-						cr.set_source_rgba (0, 0, 0, 1);+						Theme.color (cr, "Foreground 1"); 					} else {  						cr.set_source_rgba (123/255.0, 123/255.0, 123/255.0, 1); 					}@@ -233,7 +233,7 @@ public class KerningDisplay : FontDisplay { 				caret_y = get_row_height () + font.base_line + 20; 				cr.save (); 				cr.set_line_width (1.0 / KerningTools.font_size);-				cr.set_source_rgba (0, 0, 0, 0.5);+				Theme.color_opacity (cr, "Foreground 1", 0.5); 				cr.move_to (x2, caret_y + 20); 				cr.line_to (x2, 20); 				cr.stroke ();diff --git a/libbirdfont/KerningList.vala b/libbirdfont/KerningList.valaindex 7cadc23..692e971 100644--- a/libbirdfont/KerningList.vala+++ b/libbirdfont/KerningList.vala@@ -57,13 +57,13 @@ public class KerningList : FontDisplay { 		visible_rows = (int) (allocation.height / 18.0); 		 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0.3, 0.3, 0.3, 1);+		Theme.color (cr, "Background 5"); 		cr.set_font_size (12);  		classes.get_classes ((left, right, kerning) => {@@ -97,7 +97,7 @@ public class KerningList : FontDisplay {  		if (color) { 			cr.save ();-			cr.set_source_rgba (224/255.0, 224/255.0, 224/255.0, 1);+			Theme.color (cr, "Background 6"); 			cr.rectangle (0, y - 14, allocation.width, 18); 			cr.fill (); 			cr.restore ();diff --git a/libbirdfont/KerningRange.vala b/libbirdfont/KerningRange.valaindex 1ca8df1..ff58ce5 100644--- a/libbirdfont/KerningRange.vala+++ b/libbirdfont/KerningRange.vala@@ -44,12 +44,6 @@ public class KerningRange : Tool { 		});  		panel_move_action.connect ((selected, button, tx, ty) => {-			active = is_over (tx, ty);-			-			if (active) {-				TooltipArea.show_text (t_("Right click to edit the class and left click to kern glyphs in the class."));-			}-			 			return false; 		}); @@ -136,13 +130,8 @@ public class KerningRange : Tool { 		 		cr.save (); 	-		if (malformed) { -			cr.set_source_rgba (0, 0, 0, 1);-		} else if (!active) {-			cr.set_source_rgba (99/255.0, 99/255.0, 99/255.0, 1);-		} else {-			cr.set_source_rgba (0, 0, 0, 1);-		}+		// FIXME: use color to indicate error+		Theme.color (cr, "Foreground 1"); 		 		cr.set_font_size (10); 		cr.select_font_face ("Cantarell", FontSlant.NORMAL, FontWeight.NORMAL);diff --git a/libbirdfont/KeyBindings.vala b/libbirdfont/KeyBindings.valaindex 4262458..87d9c4c 100644--- a/libbirdfont/KeyBindings.vala+++ b/libbirdfont/KeyBindings.vala@@ -14,8 +14,6 @@  namespace BirdFont { -// FIXME a lot of these things have been replaced and can safely be removed- public enum Key { 	NONE = 0, 	UP = 65362,diff --git a/libbirdfont/LabelTool.vala b/libbirdfont/LabelTool.valaindex ca9f2d7..8af0e38 100644--- a/libbirdfont/LabelTool.vala+++ b/libbirdfont/LabelTool.vala@@ -55,7 +55,7 @@ public class LabelTool : Tool { 		// background 		if (is_selected ()) { 			cr.save ();-			cr.set_source_rgba (38 / 255.0, 39 / 255.0, 43 / 255.0, 1);+			Theme.color (cr, "Background 3"); 			cr.rectangle (0, y - 2, w, h + 7); 			cr.fill (); 			cr.restore ();		@@ -68,9 +68,9 @@ public class LabelTool : Tool { 		text_height = 18;  		if (is_selected ()) {-			label_text.set_source_rgba (1, 1, 1, 1);+			Theme.text_color (label_text, "Background 1"); 		} else {-			label_text.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+			Theme.text_color (label_text, "Foreground 2"); 		} 		 		label_text.set_font_size (text_height);@@ -98,9 +98,9 @@ public class LabelTool : Tool { 			center_y = bgy + ((!) counter_background).get_height () / 2.0 + 4 / scale; 			 			if (is_selected ()) {-				glyph_count.set_source_rgba (1, 1, 1, 1);+				Theme.text_color (glyph_count, "Background 1"); 			} else {-				glyph_count.set_source_rgba (51 / 255.0, 54 / 255.0, 59 / 255.0, 1);+				Theme.text_color (glyph_count, "Background 4"); 			} 			 			glyph_count.set_font_size (text_height);diff --git a/libbirdfont/LanguageSelectionTab.vala b/libbirdfont/LanguageSelectionTab.valaindex 9fba60e..480e954 100644--- a/libbirdfont/LanguageSelectionTab.vala+++ b/libbirdfont/LanguageSelectionTab.vala@@ -55,13 +55,13 @@ public class LanguageSelectionTab : FontDisplay { 		visible_rows = (int) (allocation.height / 18.0); 		 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0.3, 0.3, 0.3, 1);+		Theme.color (cr, "Background 5"); 		cr.set_font_size (12); 		 		foreach (string language in DefaultLanguages.names) {@@ -78,7 +78,7 @@ public class LanguageSelectionTab : FontDisplay {  		if (color) { 			cr.save ();-			cr.set_source_rgba (224/255.0, 224/255.0, 224/255.0, 1);+			Theme.color (cr, "Background 6"); 			cr.rectangle (0, y - 14, allocation.width, 18); 			cr.fill (); 			cr.restore ();diff --git a/libbirdfont/Line.vala b/libbirdfont/Line.valaindex 3f2afbe..edc10fa 100644--- a/libbirdfont/Line.vala+++ b/libbirdfont/Line.vala@@ -51,10 +51,7 @@ public class Line : GLib.Object { 		dashed = false; 		metrics = ""; 		-		r = 0.7;-		g = 0.7;-		b = 0.8;-		a = 1;+		set_color_theme ("Guide 1"); 	} 	 	public Line copy () {@@ -102,6 +99,15 @@ public class Line : GLib.Object { 		moveable = m; 	} 	+	public void set_color_theme (string color) {+		Color c = Theme.get_color (color);+		+		r = c.r;+		g = c.g;+		b = c.b;+		a = c.a;+	}+	 	public void set_color (double r, double g, double b, double a) { 		this.r = r; 		this.g = g;@@ -304,7 +310,7 @@ public class Line : GLib.Object { 		} 		 		if (active) {-			cr.set_source_rgba (0, 0, 0.3, 1);+			Theme.color (cr, "Highlighted Guide"); 		} else { 			cr.set_source_rgba (r, this.g, b, a); 		}@@ -330,7 +336,7 @@ public class Line : GLib.Object { 				 				if (get_active ()) {  					glyph_metrics = new Text (metrics, 17);-					glyph_metrics.set_source_rgba (72 / 255.0, 72 / 255.0, 72 / 255.0, 1);+					Theme.text_color (glyph_metrics, "Highlighted Guide"); 					glyph_metrics.widget_x = p + 10; 					glyph_metrics.widget_y = h - 25; 					glyph_metrics.draw (cr);@@ -371,7 +377,7 @@ public class Line : GLib.Object { 			} 			 			if (active) {-				line_label.set_source_rgba (0, 0, 0.3, 1);+				Theme.text_color (line_label, "Highlighted Guide"); 			} else { 				line_label.set_source_rgba (r, this.g, b, a); 			}diff --git a/libbirdfont/MainWindow.vala b/libbirdfont/MainWindow.valaindex 8a1504d..41053ad 100644--- a/libbirdfont/MainWindow.vala+++ b/libbirdfont/MainWindow.vala@@ -21,7 +21,6 @@ public class MainWindow : GLib.Object { 	public static MainWindow singleton;
 	public static MenuTab menu_tab;
 	public static FileTab file_tab;
-	public static TooltipArea tooltip;
 	public static OverView over_view;	
 	public static TabBar tabs;
 	public static NativeWindow native_window;
@@ -44,7 +43,6 @@ public class MainWindow : GLib.Object { 		tools = new Toolbox (glyph_canvas, tabs);
 		menu_tab = new MenuTab ();
 		file_tab = new FileTab ();
-		tooltip = new TooltipArea ();
 		over_view = new OverView();
 		kerning_display = new KerningDisplay ();
 		character_database = new CharDatabase ();
@@ -177,10 +175,6 @@ public class MainWindow : GLib.Object { 		return tabs.get_selected_tab ();
 	}
 
-	public static TooltipArea get_tooltip () {
-		return tooltip;
-	}
-
 	public static bool select_tab (Tab t) {
 		return tabs.selected_open_tab (t);
 	}
diff --git a/libbirdfont/Menu.vala b/libbirdfont/Menu.valaindex ae2d876..596ebf6 100644--- a/libbirdfont/Menu.vala+++ b/libbirdfont/Menu.vala@@ -359,7 +359,7 @@ public class Menu : GLib.Object { 		}); 		kerning_menu.items.add (list_kernings); -		MenuItem show_spacing = add_menu_item (t_("Spacing Classes"), "show spacing tab");+		MenuItem show_spacing = add_menu_item (t_("Spacing Classes"), "show spacing classes"); 		show_spacing.action.connect (() => { 			MenuTab.show_spacing_class_tab (); 			show_menu = false;@@ -660,7 +660,7 @@ public class Menu : GLib.Object { 		 		foreach (MenuItem item in current_menu.items) { 			cr.save ();-			cr.set_source_rgba (38 / 255.0, 39 / 255.0, 43 / 255.0, 1);+			Theme.color (cr, "Background 3"); 			cr.rectangle (x, y, width, height); 			cr.fill (); 			cr.restore ();@@ -668,7 +668,7 @@ public class Menu : GLib.Object { 			cr.save (); 			label_x = allocation.width - width + 0.7 * height * MainWindow.units; 			label_y = y + font_size - 1 * MainWindow.units;-			item.label.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+			Theme.text_color (item.label, "Foreground 2"); 			item.label.draw_at_baseline (cr, label_x, label_y); 			 			key_binding.set_text (item.get_key_bindings ());@@ -676,7 +676,7 @@ public class Menu : GLib.Object { 			binding_extent = key_binding.get_extent (); 			label_x = x + width - binding_extent - 0.6 * height * MainWindow.units; 			key_binding.set_font_size (font_size);-			key_binding.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+			Theme.text_color (key_binding, "Foreground 2"); 			key_binding.draw_at_baseline (cr, label_x, label_y); 			 			y += height;@@ -699,11 +699,12 @@ public class Menu : GLib.Object { 		} 		 		try {-		os = new DataOutputStream (file.create (FileCreateFlags.REPLACE_DESTINATION));-		os.put_string ("""<?xml version="1.0" encoding="utf-8" standalone="yes"?>""");-		os.put_string ("\n");-		-		os.put_string ("<bindings>\n");+			os = new DataOutputStream (file.create (FileCreateFlags.REPLACE_DESTINATION));+			os.put_string ("""<?xml version="1.0" encoding="utf-8" standalone="yes"?>""");+			os.put_string ("\n");+			+			os.put_string ("<bindings>\n");+			 			foreach (MenuItem item in sorted_menu_items) { 				os.put_string ("\t<action "); 				diff --git a/libbirdfont/MenuAction.vala b/libbirdfont/MenuAction.valaindex 0043b51..6823f18 100644--- a/libbirdfont/MenuAction.vala+++ b/libbirdfont/MenuAction.vala@@ -43,7 +43,7 @@ public class MenuAction : GLib.Object { 		 		if (selected) { 			cr.save ();-			cr.set_source_rgba (234/255.0, 234/255.0, 234/255.0, 1);+			Theme.color (cr, "Selected Menu Item"); 			cr.rectangle (x - 2, y - 12, 93, 15); 			cr.fill_preserve (); 			cr.stroke ();@@ -59,7 +59,8 @@ public class MenuAction : GLib.Object { 		} 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0, 1);+		+		Theme.color (cr, "Foreground 1"); 		 		cr.set_font_size (12); 		cr.select_font_face ("Cantarell", FontSlant.NORMAL, FontWeight.NORMAL);diff --git a/libbirdfont/MessageDialog.vala b/libbirdfont/MessageDialog.valaindex 12c6273..0c5fa23 100644--- a/libbirdfont/MessageDialog.vala+++ b/libbirdfont/MessageDialog.vala@@ -51,19 +51,19 @@ public class MessageDialog : Dialog { 		cy = (allocation.height - height) / 2.0; 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0, 0.3);+		Theme.color_opacity (cr, "Foreground 1", 0.3); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+		Theme.color (cr, "Background 2"); 		draw_rounded_rectangle (cr, cx, cy, width, height, 10 * MainWindow.units); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0, 1);+		Theme.color (cr, "Foreground 1"); 		cr.set_line_width (1); 		draw_rounded_rectangle (cr, cx, cy, width, height, 10 * MainWindow.units); 		cr.stroke ();diff --git a/libbirdfont/MoveTool.vala b/libbirdfont/MoveTool.valaindex 1107eff..3be9e7f 100644--- a/libbirdfont/MoveTool.vala+++ b/libbirdfont/MoveTool.vala@@ -228,7 +228,7 @@ public class MoveTool : Tool { 		 		cr.save (); 		-		cr.set_source_rgba (0, 0, 0.3, 1);+		Theme.color (cr, "Background 4"); 		cr.set_line_width (2); 		cr.rectangle (x, y, w, h); 		cr.stroke ();diff --git a/libbirdfont/OverView.vala b/libbirdfont/OverView.valaindex d75e697..4df4b78 100644--- a/libbirdfont/OverView.vala+++ b/libbirdfont/OverView.vala@@ -439,7 +439,8 @@ public class OverView : FontDisplay { 		 		// clear canvas 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1");+		 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore ();@@ -459,7 +460,7 @@ public class OverView : FontDisplay { 		 	void draw_empty_canvas (WidgetAllocation allocation, Context cr) { 		cr.save ();-		cr.set_source_rgba (156/255.0, 156/255.0, 156/255.0, 1);+		Theme.color (cr, "Background 7"); 		cr.move_to (30, 40); 		cr.set_font_size (18); 		cr.show_text (t_("No glyphs in this view."));@@ -1114,13 +1115,13 @@ public class OverView : FontDisplay { 		 		// background	 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 0.98);+		Theme.color_opacity (cr, "Background 1", 0.98); 		cr.rectangle (x, y, w, h); 		cr.fill (); 		cr.restore ();  		cr.save ();-		cr.set_source_rgba (0, 0, 0, 0.98);+		Theme.color_opacity (cr, "Foreground 1", 0.98); 		cr.set_line_width (2); 		cr.rectangle (x, y, w, h); 		cr.stroke ();@@ -1172,7 +1173,7 @@ public class OverView : FontDisplay { 	void draw_info_line (string line, Context cr, double x, double y, int row) { 		cr.save (); 		cr.set_font_size (12);-		cr.set_source_rgba (0, 0, 0, 1);+		Theme.color (cr, "Foreground 1"); 		cr.move_to (x + 10, y + 28 + row * 18 * 1.2); 		cr.show_text (line); 		cr.restore ();		diff --git a/libbirdfont/OverViewItem.vala b/libbirdfont/OverViewItem.valaindex c2cb346..3c1ce83 100644--- a/libbirdfont/OverViewItem.vala+++ b/libbirdfont/OverViewItem.vala@@ -97,13 +97,13 @@ public class OverViewItem : GLib.Object {  	public void draw (Context cr) { 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (x, y, width, height); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0, 1);+		Theme.color (cr, "Foreground 1"); 		cr.rectangle (x, y, width, height); 		cr.set_line_width (0.5); 		cr.stroke ();@@ -234,7 +234,7 @@ public class OverViewItem : GLib.Object {  		cr.save (); 		cr.set_font_size (14);-		cr.set_source_rgba (0, 0, 0, 1);+		Theme.color (cr, "Foreground 1"); 		cr.move_to (x + 0.08 * width, y + height - 6); 		 		if (glyphs == null) {diff --git a/libbirdfont/Path.vala b/libbirdfont/Path.valaindex 3d5cbe5..419924e 100644--- a/libbirdfont/Path.vala+++ b/libbirdfont/Path.vala@@ -211,7 +211,7 @@ public class Path { 		 		cr.save (); 		-		cr.set_source_rgba (0, 0, 0.3, 1);+		Theme.color (cr, "Background 4"); 		cr.set_line_width (2); 		cr.rectangle (x, y, x2 - x, y2 - y); 		cr.stroke ();@@ -1617,7 +1617,7 @@ public class Path { 			cr.save (); 			 			all_of_path ((x, y) => {-				//cr.set_source_rgba (0.3, 0.3, 0.3, 1);+				//Theme.color (cr, "Background 5"); 				cr.move_to (px + xc, -py + yc); 				cr.line_to (x + xc, -y + yc); 				diff --git a/libbirdfont/PenTool.vala b/libbirdfont/PenTool.valaindex 4a9b99f..39cd4aa 100644--- a/libbirdfont/PenTool.vala+++ b/libbirdfont/PenTool.vala@@ -1225,7 +1225,7 @@ public class PenTool : Tool { 		h = fmax (selection_box_y, selection_box_last_y) - y; 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0.3, 1);+		Theme.color (cr, "Background 4"); 		cr.set_line_width (2); 		cr.rectangle (x, y, w, h); 		cr.stroke ();diff --git a/libbirdfont/Renderer/TextArea.vala b/libbirdfont/Renderer/TextArea.valaindex f3ecf32..8d13f69 100644--- a/libbirdfont/Renderer/TextArea.vala+++ b/libbirdfont/Renderer/TextArea.vala@@ -743,7 +743,7 @@ public class TextArea : Widget { 						 						w = next_word.text; 						if (next_word.widget_y <= tt_click <= next_word.widget_y + font_size) {-							next_word.set_source_rgba (0, 0, 0, 1);+							Theme.text_color (next_word, "Foreground 1"); 							 							p = next_word.get_sidebearing_extent (); @@ -986,7 +986,7 @@ public class TextArea : Widget { 			// background 			cr.save (); 			cr.set_line_width (1);-			cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+			Theme.color (cr, "Foreground 2"); 			draw_rounded_rectangle (cr, x, y, this.width, this.height, padding); 			cr.fill (); 			cr.restore ();@@ -994,7 +994,7 @@ public class TextArea : Widget { 			// border 			cr.save (); 			cr.set_line_width (1);-			cr.set_source_rgba (0, 0, 0, 1);+			Theme.color (cr, "Foreground 1"); 			draw_rounded_rectangle (cr, x, y, this.width, this.height, padding); 			cr.stroke (); 			cr.restore ();@@ -1018,7 +1018,7 @@ public class TextArea : Widget { 			selection_stop = get_selection_stop (); 			 			cr.save ();-			cr.set_source_rgba (234 / 255.0, 77 / 255.0, 26 / 255.0, 1);+			Theme.color (cr, "Highlighted 1");  			for (int i = selection_start.paragraph; i <= selection_stop.paragraph; i++) { 				return_if_fail (0 <= i < paragraphs.size);@@ -1129,7 +1129,7 @@ public class TextArea : Widget {  		if (cache_id == -1 && paragraphs.size > 0 && paragraphs.get (0).words.size > 0) { 			Text t = paragraphs.get (0).words.get (0);-			t.set_source_rgba (0, 0, 0, 1);+			Theme.text_color (t, "Foreground 1"); 			cache_id = t.get_cache_id (); 		} 		@@ -1144,8 +1144,8 @@ public class TextArea : Widget { 				cc = new Context ((!) paragraph.cached_surface);  				foreach (Text next_word in paragraph.words) {-					next_word.set_source_rgba (0, 0, 0, 1);-+					Theme.text_color (next_word, "Foreground 1");+					 					if (next_word.text != "\n") { 						next_word.draw_at_top (cc, next_word.widget_x, next_word.widget_y - ty, cache_id); 					}diff --git a/libbirdfont/ResizeTool.vala b/libbirdfont/ResizeTool.valaindex 8b71819..c1e140d 100644--- a/libbirdfont/ResizeTool.vala+++ b/libbirdfont/ResizeTool.vala@@ -229,8 +229,7 @@ public class ResizeTool : Tool { 		cy = Glyph.reverse_path_coordinate_y (selection_box_center_y); 		 		cr.save ();-		-		cr.set_source_rgba (0, 0, 0.3, 1);+		Theme.color (cr, "Highlight 1"); 		cr.rectangle (cx - 2.5, cy - 2.5, 5, 5); 		cr.fill (); @@ -242,7 +241,7 @@ public class ResizeTool : Tool { 		cr.line_to (cx + hx, cy + hy); 		cr.stroke (); -		cr.set_source_rgba (0, 0, 0.3, 1);+		Theme.color (cr, "Highlight 1"); 		cr.rectangle (cx + hx - 2.5, cy + hy - 2.5, 5, 5); 		cr.fill (); 					diff --git a/libbirdfont/SaveDialog.vala b/libbirdfont/SaveDialog.valaindex 6b2d4fc..84020cf 100644--- a/libbirdfont/SaveDialog.vala+++ b/libbirdfont/SaveDialog.vala@@ -77,7 +77,7 @@ public class SaveDialog : Dialog { 		 		save_question.widget_x = save_button.widget_x + center; 		save_question.widget_y = cy + 15 * MainWindow.units;-		save_question.set_source_rgba (1, 1, 1, 1);+		Theme.text_color (save_question, "Background 1"); 		 		qh = (question_font_size + 1) * MainWindow.units; 		@@ -100,19 +100,19 @@ public class SaveDialog : Dialog { 		cy = (allocation.height - height) / 2.0; 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0, 0.3);+		Theme.color_opacity (cr, "Foreground 1", 0.3); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+		Theme.color (cr, "Background 2"); 		draw_rounded_rectangle (cr, cx, cy, width, height, 10 * MainWindow.units); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0, 0, 0, 1);+		Theme.color (cr, "Foreground 1"); 		cr.set_line_width (1); 		draw_rounded_rectangle (cr, cx, cy, width, height, 10 * MainWindow.units); 		cr.stroke ();diff --git a/libbirdfont/SettingsDisplay.vala b/libbirdfont/SettingsDisplay.valaindex 61e7989..2354041 100644--- a/libbirdfont/SettingsDisplay.vala+++ b/libbirdfont/SettingsDisplay.vala@@ -221,6 +221,12 @@ public class SettingsDisplay : FontDisplay { 		foreach (MenuItem menu_item in MainWindow.get_menu ().sorted_menu_items) { 			tools.add (new SettingsItem.key_binding (menu_item)); 		}+		+		tools.add (new SettingsItem.head_line (t_("Colors")));++		foreach (string color in Theme.color_list) {+			tools.add (new SettingsItem.color (color));+		}		 	}  	public override void draw (WidgetAllocation allocation, Context cr) {		@@ -232,7 +238,7 @@ public class SettingsDisplay : FontDisplay { 		cr.save (); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.set_line_width (0);-		cr.set_source_rgba (51 / 255.0, 54 / 255.0, 59 / 255.0, 1);+		Theme.color (cr, "Background 4"); 		cr.fill (); 		cr.stroke (); 		cr.restore ();diff --git a/libbirdfont/SettingsItem.vala b/libbirdfont/SettingsItem.valaindex 7bf6588..3f7c27e 100644--- a/libbirdfont/SettingsItem.vala+++ b/libbirdfont/SettingsItem.vala@@ -53,6 +53,36 @@ class SettingsItem : GLib.Object { 		handle_events = false; 		headline = true; 	}++	public SettingsItem.color (string color) {+		ColorTool cb;+		Color c;+		+		c = Theme.get_color (color);++		label = new Text ();+		label.set_text (color);+		handle_events = true;+		+		cb = new ColorTool (color);+		cb.set_r (c.r);+		cb.set_g (c.g);+		cb.set_b (c.b);+		cb.set_a (c.a);+		+		cb.color_updated.connect (() => {+			TabBar tab_bar;+			+			Theme.save_color (color, cb.color_r, cb.color_g, cb.color_b, cb.color_a);+			+			tab_bar = MainWindow.get_tab_bar ();+			tab_bar.redraw (0, 0, tab_bar.width, tab_bar.height);+			GlyphCanvas.redraw ();+			Toolbox.redraw_tool_box ();+		});+	+		button = cb;+	} 	 	public void draw (WidgetAllocation allocation, Context cr) { 		Tool t;@@ -60,20 +90,20 @@ class SettingsItem : GLib.Object { 		 		if (headline) { 			cr.save ();-			cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+			Theme.color (cr, "Background 2"); 			cr.rectangle (0, y, allocation.width, 40 * MainWindow.units); 			cr.fill (); 			cr.restore (); 				 			cr.save ();-			label.set_source_rgba (1, 1, 1, 1);+			Theme.text_color (label, "Background 1"); 			label.set_font_size (20 * MainWindow.units); 			label.draw_at_baseline (cr, 21 * MainWindow.units, y + 25 * MainWindow.units); 			cr.restore (); 		} else { 			if (active) { 				cr.save ();-				cr.set_source_rgba (38 / 255.0, 39 / 255.0, 43 / 255.0, 1);+				Theme.color (cr, "Background 3"); 				cr.rectangle (0, y - 5 * MainWindow.units, allocation.width, 40 * MainWindow.units); 				cr.fill (); 				cr.restore ();@@ -88,7 +118,7 @@ class SettingsItem : GLib.Object { 			} 			 			cr.save ();-			label.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+			Theme.text_color (label, "Foreground 2"); 			label.set_font_size (17 * MainWindow.units); 			label.draw_at_baseline (cr, label_x, y + 20 * MainWindow.units); 			cr.restore ();@@ -99,9 +129,9 @@ class SettingsItem : GLib.Object { 				cr.save (); 				 				if (active) {-					key_binding_text.set_source_rgba (1, 1, 1, 1);+					Theme.text_color (key_binding_text, "Background 1"); 				} else {-					key_binding_text.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+					Theme.text_color (key_binding_text, "Foreground 2"); 				} 				 				key_binding_text.set_font_size (17 * MainWindow.units);diff --git a/libbirdfont/SpacingTab.vala b/libbirdfont/SpacingTab.valaindex ba21fad..f60a312 100644--- a/libbirdfont/SpacingTab.vala+++ b/libbirdfont/SpacingTab.vala@@ -51,14 +51,14 @@ public class SpacingTab : KerningDisplay {  		// background 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (0, allocation.height - height, allocation.width, height); 		cr.fill (); 		cr.restore (); 		 		// character bar 		cr.save ();-		cr.set_source_rgba (0.5, 0.5, 0.5, 1);+		Theme.color (cr, "Foreground 3"); 		cr.set_line_width (0.8); 		cr.move_to (0, allocation.height - height); 		cr.line_to (allocation.width, allocation.height - height);@@ -112,21 +112,21 @@ public class SpacingTab : KerningDisplay { 			 			c = g.get_unichar (); 			cap = new Text ((!) c.to_string (), 17);-			cap.set_source_rgba (72 / 255.0, 72 / 255.0, 72 / 255.0, 1);+			Theme.text_color (cap, "Foreground 3"); 			cap.widget_x = middle - cap.get_extent () / 2.0; 			cap.widget_y = allocation.height - height + character_height - 4 * MainWindow.units; 			cap.draw_at_baseline (cr, cap.widget_x, cap.widget_y);			 			 			l = g.get_left_side_bearing (); 			left = new Text (truncate (l, 5), 17);-			left.set_source_rgba (72 / 255.0, 72 / 255.0, 72 / 255.0, 1);+			Theme.text_color (left, "Foreground 3"); 			left.widget_x = middle - box_size / 2.0 + (box_size / 2.0 - left.get_extent ()) / 2.0; 			left.widget_y = allocation.height - 7 * MainWindow.units; 			left.draw_at_baseline (cr, left.widget_x, left.widget_y);  			r = g.get_right_side_bearing (); 			right = new Text (truncate (r, 5), 17);-			right.set_source_rgba (72 / 255.0, 72 / 255.0, 72 / 255.0, 1);+			Theme.text_color (right, "Foreground 3"); 			right.widget_x = end - (box_size / 2.0 - right.get_extent ()) / 2.0 - right.get_extent (); 			right.widget_y = allocation.height - 7 * MainWindow.units; 			right.draw_at_baseline (cr, right.widget_x, right.widget_y);					diff --git a/libbirdfont/SpinButton.vala b/libbirdfont/SpinButton.valaindex 9d2f1f3..a66cc46 100644--- a/libbirdfont/SpinButton.vala+++ b/libbirdfont/SpinButton.vala@@ -447,9 +447,7 @@ public class SpinButton : Tool { 	 		if (!show_icon_tool_icon || waiting_for_icon_switch) { 			cr.save ();-		-			cr.set_source_rgba (101 / 255.0, 106 / 255.0, 115 / 255.0, 1);-			+			Theme.color (cr, "Background 2"); 			cr.set_font_size (10 * scale); 			cr.select_font_face ("Cantarell", FontSlant.NORMAL, FontWeight.NORMAL); 			diff --git a/libbirdfont/TabBar.vala b/libbirdfont/TabBar.valaindex 417eb0d..7cea816 100644--- a/libbirdfont/TabBar.vala+++ b/libbirdfont/TabBar.vala@@ -18,8 +18,8 @@ namespace BirdFont {  public class TabBar : GLib.Object { 	-	int width = 0;-	int height = 0;+	public int width = 0;+	public int height = 0; 	 	public Gee.ArrayList<Tab> tabs; @@ -677,7 +677,7 @@ public class TabBar : GLib.Object { 			if (menu_icon != null) { 				 				if (MainWindow.get_menu ().show_menu) {-					cr.set_source_rgba (38 / 255.0, 39 / 255.0, 43 / 255.0, 1);+					Theme.color (cr, "Background 3"); 					cr.rectangle (w - 32 / scale, 0, 32 / scale, h); 					cr.fill (); 				}@@ -731,19 +731,19 @@ public class TabBar : GLib.Object { 			// background 			if (tab_index == selected) { 				cr.save ();-				cr.set_source_rgba (234 / 255.0, 77 / 255.0, 26 / 255.0, 1);+				Theme.color (cr, "Highlighted 1"); 				cr.rectangle (0, 0, tab_width, h); 				cr.fill (); 				cr.restore ();				 			} else if (tab_index == over) { 				cr.save ();-				cr.set_source_rgba (56 / 255.0, 59 / 255.0, 65 / 255.0, 1);+				Theme.color (cr, "Backgrund 7"); 				cr.rectangle (0, 0, tab_width, h); 				cr.fill (); 				cr.restore ();			 			} else { 				cr.save ();-				cr.set_source_rgba (51 / 255.0, 54 / 255.0, 59 / 255.0, 1);+				Theme.color (cr, "Background 4"); 				cr.rectangle (0, 0, tab_width, h); 				cr.fill (); 				cr.restore ();@@ -758,9 +758,9 @@ public class TabBar : GLib.Object { 				close_opacity = (over_close_tab == tab_index) ? 1 : 0.2;   				if (tab_index == selected) {-					cr.set_source_rgba (40 / 255.0, 57 / 255.0, 65 / 255.0, close_opacity);+					Theme.color_opacity (cr, "Foreground 4", close_opacity); 				} else {-					cr.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, close_opacity);+					Theme.color_opacity (cr, "Foreground 2", close_opacity); 				} 				 				cr.move_to (tab_width - 7 / scale, h / 2.0 - 2.5 / scale);@@ -783,9 +783,9 @@ public class TabBar : GLib.Object { 			center_y = tab_height / 2.0 + 4 / scale; 			 			if (tab_index == selected) {-				label.set_source_rgba (40 / 255.0, 57 / 255.0, 65 / 255.0, 1);+				Theme.text_color (label, "Foreground 4"); 			} else {-				label.set_source_rgba (101 / 255.0, 108 / 255.0, 116 / 255.0, 1);+				Theme.text_color (label, "Foreground 2"); 			} 			 			label.set_font_size (text_height);@@ -795,7 +795,7 @@ public class TabBar : GLib.Object { 			if (tab_index != selected) { // don't draw edges for the selected tab 				if (tab_index + 1 != selected) { 					cr.save ();-					cr.set_source_rgba (70 / 255.0, 77 / 255.0, 83 / 255.0, 1);+					Theme.color (cr, "Foreground 5"); 					cr.rectangle (tab_width - 1 / scale, 0, 1 / scale, h); 					cr.fill (); 					cr.restore ();@@ -803,7 +803,7 @@ public class TabBar : GLib.Object { 				 				if (tab_index == first_tab) { 					cr.save ();-					cr.set_source_rgba (70 / 255.0, 77 / 255.0, 83 / 255.0, 1);+					Theme.color (cr, "Foreground 5"); 					cr.rectangle (0, 0, 1 / scale, h); 					cr.fill (); 					cr.restore ();diff --git a/libbirdfont/TabContent.vala b/libbirdfont/TabContent.valaindex 2f18cbb..44783a0 100644--- a/libbirdfont/TabContent.vala+++ b/libbirdfont/TabContent.vala@@ -64,7 +64,7 @@ public class TabContent : GLib.Object { 		 		if (unlikely (MenuTab.suppress_event)) { 			cr.save ();-			cr.set_source_rgba (1, 1, 1, 1);+			Theme.color (cr, "Background 1"); 			cr.rectangle (0, 0, allocation.width, allocation.height); 			cr.fill (); 			cr.restore ();diff --git a/libbirdfont/Table.vala b/libbirdfont/Table.valaindex 2e6da18..85cc699 100644--- a/libbirdfont/Table.vala+++ b/libbirdfont/Table.vala@@ -43,13 +43,13 @@ public abstract class Table : FontDisplay { 		visible_rows = (int) (allocation.height / 18.0); 		 		cr.save ();-		cr.set_source_rgba (1, 1, 1, 1);+		Theme.color (cr, "Background 1"); 		cr.rectangle (0, 0, allocation.width, allocation.height); 		cr.fill (); 		cr.restore (); 		 		cr.save ();-		cr.set_source_rgba (0.3, 0.3, 0.3, 1);+		Theme.color (cr, "Background 5"); 		cr.set_font_size (12);  		foreach (Row r in get_rows ()) {@@ -70,7 +70,7 @@ public abstract class Table : FontDisplay { 	 		if (color) { 			cr.save ();-			cr.set_source_rgba (224/255.0, 224/255.0, 224/255.0, 1);+			Theme.color (cr, "Background 6"); 			cr.rectangle (0, y - 14 * MainWindow.units, allocation.width, 18 * MainWindow.units); 			cr.fill (); 			cr.restore ();diff --git a/libbirdfont/Theme.vala b/libbirdfont/Theme.valanew file mode 100644index 0000000..51b967a--- /dev/null+++ b/libbirdfont/Theme.vala@@ -0,0 +1,202 @@+/*+    Copyright (C) 2015 Johan Mattsson++    This library is free software; you can redistribute it and/or modify +    it under the terms of the GNU Lesser General Public License as +    published by the Free Software Foundation; either version 3 of the +    License, or (at your option) any later version.++    This library is distributed in the hope that it will be useful, but +    WITHOUT ANY WARRANTY; without even the implied warranty of +    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +    Lesser General Public License for more details.+*/++using Bird;+using Cairo;++namespace BirdFont {++public class Theme : GLib.Object {++	static Gee.HashMap<string, Color> colors;+	public static Gee.ArrayList<string> color_list;++	public static void text_color (Text text, string name) {+		Color c;+		+		if (unlikely (!colors.has_key (name))) {+			warning (@"Theme does not have a color for $name");+			return;+		}+		+		c = colors.get (name);+		text.set_source_rgba (c.r, c.g, c.b, c.a);+	}++	public static void color (Context cr, string name) {+		Color c;+		+		if (unlikely (!colors.has_key (name))) {+			warning (@"Theme does not have a color for $name");+			return;+		}+		+		c = colors.get (name);+		cr.set_source_rgba (c.r, c.g, c.b, c.a);+	}++	public static void color_opacity (Context cr, string name, double opacity) {+		Color c;+		+		if (unlikely (!colors.has_key (name))) {+			warning (@"Theme does not have a color for $name");+			return;+		}+		+		c = colors.get (name);+		cr.set_source_rgba (c.r, c.g, c.b, opacity);+	}++	public static void text_color_opacity (Text text, string name, double opacity) {+		Color c;+		+		if (unlikely (!colors.has_key (name))) {+			warning (@"Theme does not have a color for $name");+			return;+		}+		+		c = colors.get (name);+		text.set_source_rgba (c.r, c.g, c.b, opacity);+	}+	public static Color get_color (string name) {+		Color c;+		+		if (unlikely (!colors.has_key (name))) {+			warning (@"Theme does not have a color for $name");+			return new Color (0, 0, 0, 1);+		}+		+		return colors.get (name);+	}+	+	public static void save_color (string name, double r, double g, double b, double a) {+		colors.set (name, new Color (r, g, b, a));+		write_theme ();+	}++	public static void load_theme () {+		File default_theme = SearchPaths.find_file (null, "theme.xml");+		File user_theme = get_child (BirdFont.get_settings_directory (), "theme.xml");++		colors = new Gee.HashMap<string, Color> ();+		color_list = new Gee.ArrayList<string> ();+		+		if (default_theme.query_exists ()) {+			parse_theme (default_theme);+		}++		if (user_theme.query_exists ()) {+			parse_theme (user_theme);+		}+		+		color_list.sort ();+	}++	public static void write_theme () {+		DataOutputStream os;+		File file;++		file = get_child (BirdFont.get_settings_directory (), "theme.xml");+		+		try {+			if (file.query_exists ()) {+				file.delete ();+			}+		} catch (GLib.Error e) {+			warning (e.message);+		}+		+		try {+			os = new DataOutputStream (file.create (FileCreateFlags.REPLACE_DESTINATION));+			os.put_string ("""<?xml version="1.0" encoding="utf-8" standalone="yes"?>""");+			os.put_string ("\n");+			+			os.put_string ("<theme>\n");+			foreach (string name in colors.keys) {+				Color color = colors.get (name);+				+				os.put_string ("\t<color ");+				+				os.put_string (@"name=\"$(Markup.escape_text (name))\" ");				+				os.put_string (@"red=\"$(color.r)\" ");+				os.put_string (@"green=\"$(color.g)\" ");+				os.put_string (@"blue=\"$(color.b)\" ");+				os.put_string (@"alpha=\"$(color.a)\"");+				+				os.put_string ("/>\n");+			}+			os.put_string ("</theme>\n");+			+			os.close ();+		} catch (GLib.Error e) {+			warning (e.message);+		}+	}++	static void parse_theme (File f) {+		string xml_data;+		XmlParser parser;+		+		try {+			FileUtils.get_contents((!) f.get_path (), out xml_data);+			parser = new XmlParser (xml_data);+			parse_colors (parser.get_root_tag ());+		} catch (GLib.Error e) {+			warning (e.message);+		}+	}+	+	static void parse_colors (Tag tag) {+		foreach (Tag t in tag) {+			if (t.get_name () == "color") {+				parse_color (t.get_attributes ());+			}+		}+	}+	+	static void parse_color (Attributes attributes) {+		string name = "";+		double r = 0;+		double g = 0;+		double b = 0;+		double a = 1;+		+		foreach (Attribute attr in attributes) {+			if (attr.get_name () == "name") {+				name = attr.get_content ();+			}+						+			if (attr.get_name () == "red") {+				r = double.parse (attr.get_content ());+			}+			+			if (attr.get_name () == "green") {+				g = double.parse (attr.get_content ());+			}+			+			if (attr.get_name () == "blue") {+				b = double.parse (attr.get_content ());+			}++			if (attr.get_name () == "alpha") {+				a = double.parse (attr.get_content ());+			}+		}+		+		color_list.add (name);+		colors.set (name, new Color (r, g, b, a));+	}+}++}diff --git a/libbirdfont/Tool.vala b/libbirdfont/Tool.valaindex f4478af..3d3db44 100644--- a/libbirdfont/Tool.vala+++ b/libbirdfont/Tool.vala@@ -105,7 +105,6 @@ public class Tool : GLib.Object { 		next_id++; 		 		panel_press_action.connect ((self, button, x, y) => {-			MainWindow.get_tooltip ().set_text_from_tool (); 		}); 		 		move_out_action.connect ((self) => {@@ -214,10 +213,7 @@ public class Tool : GLib.Object { 		return (x <= xp <= x + w  && y <= yp <= y + h);   	} 	-	public bool set_selected (bool a) {-		TooltipArea? tpa = null;					-		tpa = MainWindow.get_tooltip ();-							+	public bool set_selected (bool a) {						 		new_selection = true; 		selected = a; 		set_active (a);diff --git a/libbirdfont/Toolbox.vala b/libbirdfont/Toolbox.valaindex 2af856e..e3211de 100644--- a/libbirdfont/Toolbox.vala+++ b/libbirdfont/Toolbox.vala@@ -233,7 +233,6 @@ public class Toolbox : GLib.Object  { 		bool a; 		bool consumed = false; 		bool active;-		TooltipArea? tpa = null; 					 		foreach (Expander exp in current_set.get_expanders ()) { 			a = exp.is_over (x, y);@@ -247,14 +246,12 @@ public class Toolbox : GLib.Object  { 			foreach (Tool t in exp.tool) { 				if (t.tool_is_visible ()) { 					active = t.is_over (x, y);-					tpa = null;-					+ 					if (!active && t.is_active ()) { 						t.move_out_action (t); 					} 					 					update = t.set_active (active);-					tpa = MainWindow.get_tooltip (); 					 					if (update) { 						redraw (0, 0, allocation_width, allocation_height);@@ -453,7 +450,7 @@ public class Toolbox : GLib.Object  { 			 			cr.rectangle (0, 0, w, h); 			cr.set_line_width (0);-			cr.set_source_rgba (51/255.0, 54/255.0, 59/255.0, 1);+			Theme.color (cr, "Background 4"); 			cr.fill ();  			draw_expanders (w, h, cr);diff --git a/libbirdfont/TooltipArea.vala b/libbirdfont/TooltipArea.valadeleted file mode 100644index ab773b2..0000000--- a/libbirdfont/TooltipArea.vala+++ /dev/null@@ -1,123 +0,0 @@-/*-    Copyright (C) 2012 2013 Johan Mattsson--    This library is free software; you can redistribute it and/or modify -    it under the terms of the GNU Lesser General Public License as -    published by the Free Software Foundation; either version 3 of the -    License, or (at your option) any later version.--    This library is distributed in the hope that it will be useful, but -    WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -    Lesser General Public License for more details.-*/--using Cairo;--namespace BirdFont {--public class TooltipArea : GLib.Object {-	string tooltip;-	-	public signal void redraw ();--	public TooltipArea () {-		set_text_from_tool ();-	}--	public void update_text () {-		set_text_from_current_tool ();-		redraw ();-	}-	-	public static void show_text (string text) {-		IdleSource idle = new IdleSource ();-		idle.set_callback (() => {-			if (!is_null (MainWindow.get_tooltip ())) {-				MainWindow.get_tooltip ().tooltip = text;-				MainWindow.get_tooltip ().redraw ();-			}-			return false;-		});-		idle.attach (null);-	}-	-	public void set_text_from_tool () {-		set_text_from_current_tool ();-		redraw ();-	}-	-	private void set_text_from_current_tool () {-		Toolbox? tb = MainWindow.get_toolbox ();-		Tool? t;-		Tool tool;-		StringBuilder sb;-		-		if (tb == null) {-			return;-		}-		-		t = ((!)tb).get_active_tool ();-		-		if (t == null) {-			return;-		}-		-		tool = (!) t;-		-		if (tool.key != '\0') {-			sb = new StringBuilder ();--			sb.append ("(");-			-			if (tool.modifier_flag == CTRL) {-				sb.append ("Ctrl+");-			} else if (tool.modifier_flag == SHIFT) {-				sb.append ("Shift+");-			} --			sb.append_unichar (tool.key);-			sb.append (") ");-			sb.append (tool.get_tip ());-			-			show_text (sb.str);-		} else {-			show_text (tool.get_tip ());-		}-		-	}-	-	public void draw (Context cr, WidgetAllocation alloc) {-		cr.save ();-		cr.rectangle (0, 0, alloc.width, alloc.height);-		cr.set_line_width (0);-		cr.set_source_rgba (200/255.0, 200/255.0, 200/255.0, 1);-		cr.fill_preserve ();-		cr.stroke ();-		cr.restore ();--		cr.save ();-		cr.rectangle (0, 0, alloc.width, 1);-		cr.set_line_width (0);-		cr.set_source_rgba (127/255.0, 127/255.0, 127/255.0, 1);-		cr.fill_preserve ();-		cr.stroke ();-		cr.restore ();-		-		cr.save ();-		cr.rectangle (0, 1, alloc.width, 1);-		cr.set_line_width (0);-		cr.set_source_rgba (170/255.0, 170/255.0, 170/255.0, 1);-		cr.fill_preserve ();-		cr.stroke ();-		cr.restore ();-		-		cr.save ();-		cr.set_font_size (14);-		cr.move_to (5, 15);-		cr.show_text (tooltip);-		cr.restore ();-	}-}--}diff --git a/libbirdfont/ZoomBar.vala b/libbirdfont/ZoomBar.valaindex cae847c..e4bac1f 100644--- a/libbirdfont/ZoomBar.vala+++ b/libbirdfont/ZoomBar.vala@@ -86,21 +86,21 @@ public class ZoomBar : Tool { 		 		// filled 		cr.save ();-		cr.set_source_rgba (26 / 255.0, 30 / 255.0, 32 / 255.0, 1);+		Theme.color (cr, "Foreground 3"); 		draw_bar (cr); 		cr.fill (); 		cr.restore (); 		 		// remove non filled parts 		cr.save ();-		cr.set_source_rgba (51 / 255.0, 54 / 255.0, 59 / 255.0, 1);+		Theme.color (cr, "Background 4"); 		cr.rectangle (x + bar_width * zoom_level, y, w, h); 		cr.fill (); 		cr.restore (); 		 		// border 		cr.save ();-		cr.set_source_rgba (26 / 255.0, 30 / 255.0, 32 / 255.0, 1);+		Theme.color (cr, "Foreground 1"); 		cr.set_line_width (0.8); 		draw_bar (cr); 		cr.stroke ();diff --git a/resources/key_bindings.xml b/resources/key_bindings.xmlindex b22fb30..a31688d 100644--- a/resources/key_bindings.xml+++ b/resources/key_bindings.xml@@ -1,6 +1,6 @@ <?xml version="1.0" encoding="utf-8" standalone="yes"?> <bindings>-	<action key="n" ctrl="false" alt="true" command="false" shift="false" action="new" />+	<action key="n" ctrl="true" alt="false" command="false" shift="false" action="new" /> 	<action key="o" ctrl="true" alt="false" command="false" shift="false" action="open" /> 	<action key="r" ctrl="true" alt="false" command="false" shift="false" action="recent files" /> 	<action key="s" ctrl="true" alt="false" command="false" shift="false" action="save" />@@ -25,6 +25,8 @@ 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="glyph sequence" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="set background glyph" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="remove background glyph" />+	<action key="" ctrl="false" alt="false" command="false" shift="false" action="create guide" />+	<action key="" ctrl="false" alt="false" command="false" shift="false" action="show guide tab" /> 	<action key="r" ctrl="true" alt="false" command="false" shift="false" action="select point above" /> 	<action key="s" ctrl="true" alt="false" command="false" shift="false" action="select next point" /> 	<action key="q" ctrl="true" alt="false" command="false" shift="false" action="select previous point" />@@ -33,9 +35,10 @@ 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="previous tab" /> 	<action key="w" ctrl="true" alt="false" command="false" shift="false" action="close tab" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="close all tabs" />+	<action key="l" ctrl="true" alt="false" command="false" shift="false" action="show spacing tab" /> 	<action key="k" ctrl="true" alt="false" command="false" shift="false" action="show kerning tab" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="list kerning pairs" />-	<action key="" ctrl="false" alt="false" command="false" shift="false" action="show spacing tab" />+	<action key="" ctrl="false" alt="false" command="false" shift="false" action="show spacing classes" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="select next kerning pair" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="select previous kerning pair" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="show ligature tab" />@@ -92,13 +95,12 @@ 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="next" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="circle" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="rectangle" />+	<action key="" ctrl="false" alt="false" command="false" shift="false" action="test_case" />+	<action key="" ctrl="false" alt="false" command="false" shift="false" action="slow_test" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="kerning_class" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="kerning_text_input" />-	<action key="" ctrl="false" alt="false" command="false" shift="false" action="side_bearings" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="insert_last_glyph" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="insert_unichar" />-	<action key="" ctrl="false" alt="false" command="false" shift="false" action="kerning_font_size_one" />-	<action key="" ctrl="false" alt="false" command="false" shift="false" action="kerning_font_size_two" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="update_webview" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="export_fonts" /> 	<action key="" ctrl="false" alt="false" command="false" shift="false" action="generate_html_document" />

Contact

Email: johan.mattsson.m@gmail.com
Mastodon: typo.social/@birdfont
GitHub: johanmattssonm
LinkedIn: johan-mattsson-2ab324112