Clone in a terminal:
Commit 4a343aa
Johan Mattsson - 2015-12-16T01:32:58+00:00
4a343aae6b6200f30aaa623ee24718f0aebf042ejohan.mattsson.m@gmail.com

More speed optimizations in the overview tab

Changed files (3)

Diff

diff --git a/libbirdfont/GlyphRange.vala b/libbirdfont/GlyphRange.valaindex 1c82d17..c7e5bcd 100644--- a/libbirdfont/GlyphRange.vala+++ b/libbirdfont/GlyphRange.vala@@ -28,6 +28,7 @@ public class GlyphRange { 	bool range_is_class = false; 	uint32* range_index = null; 	int index_size = 0;+	int index_hint = 0; 	 	public GlyphRange () { 		ranges = new Gee.ArrayList<UniRange> ();@@ -430,9 +431,15 @@ public class GlyphRange { 	private void get_unirange_index (uint32 index, out UniRange? range, out uint32 range_start_index) { 		int lower = 0; 		int upper = index_size - 1;-		int i = lower + (upper - lower) / 2;+		int i; 		int end = index_size - 1; 		+		if (index_hint >= 0 && index_hint < index_size) {+			i = index_hint;+		} else {+			i = (lower + upper) / 2;+		}+		 		range_start_index = -1; 		range = null; 		@@ -444,10 +451,12 @@ public class GlyphRange { 			if (i == end) { 				range_start_index = range_index[i]; 				range = ranges.get (i);+				index_hint = i; 				break; 			} else if (range_index[i] <= index && range_index[i + 1] > index) { 				range_start_index = range_index[i]; 				range = ranges.get (i);+				index_hint = i; 				break; 			} 			@@ -461,42 +470,50 @@ public class GlyphRange { 				upper = i - 1; 			} 			-			i = lower + (upper - lower) / 2;+			i = (lower + upper) / 2; 		} 	} 	 	public string get_char (uint32 index) {+		StringBuilder sb;+		+		sb = new StringBuilder ();+		sb.append_unichar (get_character (index));+		+		return sb.str;+	}+	+	public unichar get_character (uint32 index) { 		int64 ti; 		string chr; 		UniRange r;-		StringBuilder sb; 		unichar c;		 		UniRange? range; 		uint32 range_start_index; 		 		if (unlikely (index > len + unassigned.size)) {-			return "\0".dup();+			return '\0'; 		} 		 		if (index >= len) { 			if (unlikely (index - len >= unassigned.size)) {-				return "\0".dup();+				return '\0'; 			}  			 			chr = unassigned.get ((int) (index - len));-			return chr;+			return chr.get_char (); 		} 		 		get_unirange_index (index, out range, out range_start_index); 		 		if (unlikely (range == null)) { 			warning (@"No range found for index $index");-			return "";+			return '\0'; 		}  		 		if (unlikely (range_start_index > index || range_start_index == -1)) { 			warning ("Index out of bounds in glyph range.");-			return "";+			return '\0'; 		} 		 		r = (!) range;@@ -504,13 +521,10 @@ public class GlyphRange { 		 		if (unlikely (!c.validate ())) { 			warning ("Not a valid unicode character.");-			return "";+			return '\0'; 		} 		-		sb = new StringBuilder ();-		sb.append_unichar (c);-		-		return sb.str;+		return c; 	} 	 	public uint32 length () {diff --git a/libbirdfont/OverView.vala b/libbirdfont/OverView.valaindex ce0338b..c5f9195 100644--- a/libbirdfont/OverView.vala+++ b/libbirdfont/OverView.vala@@ -20,7 +20,7 @@ namespace BirdFont { public class OverView : FontDisplay { 	public WidgetAllocation allocation = new WidgetAllocation (); 	-	public OverViewItem selected_item = new OverViewItem (null, '\0', 0, 0);+	public OverViewItem selected_item = new OverViewItem ();  	public Gee.ArrayList<GlyphCollection> copied_glyphs = new Gee.ArrayList<GlyphCollection> (); 	public Gee.ArrayList<GlyphCollection> selected_items = new Gee.ArrayList<GlyphCollection> ();	@@ -490,7 +490,7 @@ public class OverView : FontDisplay { 	 	OverViewItem get_selected_item () { 		if (visible_items.size == 0) {-			return new OverViewItem (null, '\0', 0, 0);+			return new OverViewItem (); 		} 		 		if (!(0 <= selected < visible_items.size)) { @@ -518,7 +518,7 @@ public class OverView : FontDisplay { 		update_scheduled = true; 	} 	-	public void process_update_item_list () {+	public void process_item_list_update () { 		string character_string; 		Font f = BirdFont.get_current_font (); 		GlyphCollection? glyphs = null;@@ -529,80 +529,118 @@ public class OverView : FontDisplay { 		Glyph glyph; 		double tab_with; 		int item_list_length;+		int visible_size; 		 		Test test = new Test.time("update_item_list"); 		-		tab_with =  allocation.width - 30; // scrollbar+		tab_with = allocation.width - 30; // scrollbar 		 		items_per_row = get_items_per_row (); 		rows = (int) (allocation.height /  OverViewItem.full_height ()) + 2; 		 		item_list_length = items_per_row * rows;-		+ 		foreach  (OverViewItem overview_item in visible_items) { 			overview_item.cancel_thumbnail_rendering (); 		} 		-		visible_items = new Gee.ArrayList<OverViewItem> ();-						-		// update item list+		visible_items.clear ();+		Test test3 = new Test.time("two conditions");+		 		index = (uint32) first_visible; 		x = OverViewItem.margin; 		y = OverViewItem.margin;-		for (int i = 0; i < item_list_length; i++) {-			if (all_available) {-				if (! (0 <= index < f.length ())) {-					break;-				}-				+		+		if (all_available) {+			uint font_length = f.length ();+			+			for (int i = 0; i < item_list_length && index < font_length; i++) { 				glyphs = f.get_glyph_collection_index ((uint32) index); 				return_if_fail (glyphs != null); 				 				glyph = ((!) glyphs).get_current (); 				character_string = glyph.name; 				character = glyph.unichar_code;-			} else {-				if (!(0 <= index < glyph_range.get_length ())) {-					break;-				} 				-				character_string = glyph_range.get_char ((uint32) index);-				glyphs = f.get_glyph_collection_by_name (character_string);-				character = character_string.get_char (0);+				item = new OverViewItem ();+				item.set_glyphs (glyphs);+				item.set_character (character);+				item.x = x;+				item.y = y;+				visible_items.add (item);+				index++; 			}+		} else {++			Test test_mk = new Test.time("mk items");+			uint32 glyph_range_size = glyph_range.get_length (); 			-			x += OverViewItem.full_width ();+			for (int i = 0; i < item_list_length && index < glyph_range_size; i++) {			+				item = new OverViewItem ();+				visible_items.add (item);+			}+			warning (test_mk.get_test_time ()); 			-			if (x + OverViewItem.full_width () >= tab_with) {-				x = OverViewItem.margin;-				y += OverViewItem.full_height ();+			Test test_gl = new Test.time("get_glyph");+			visible_size = visible_items.size;+			for (int i = 0; i < visible_size; i++) {+				item = visible_items.get (i);+				glyphs = f.get_glyph_collection_by_name ((!) item.character.to_string ());+				item.set_glyphs (glyphs); 			}+			warning (test_gl.get_test_time ());++			Test test_a = new Test.time("get_char"); 			-			bool selected_item = (i == selected);+			visible_size = visible_items.size;+			for (int i = 0; i < visible_size; i++) {+				item = visible_items.get (i);+				character = glyph_range.get_character ((uint32) index);+				item.set_character (character);+				index++;+			}+			warning (test_a.get_test_time ());+		}+		+		Test test_b = new Test.time("adjust pos");+		x = OverViewItem.margin;+		y = OverViewItem.margin;+		+		visible_size = visible_items.size;+		int selected_index;+		bool selected_item;+		double full_width = OverViewItem.full_width ();+		+		for (int i = 0; i < visible_size; i++) {+			item = visible_items.get (i);++			selected_item = false; 			 			if (glyphs != null) {-				selected_item |= selected_items.index_of ((!) glyphs) != -1;+				selected_index = selected_items.index_of ((!) glyphs);+				selected_item = (selected_index != -1); 			} 			-			if (i >= visible_items.size) {-				item = new OverViewItem (glyphs, character, x, y);-				item.adjust_scale ();-				item.selected = selected_item;-				visible_items.add (item);-			} else {-				visible_items.get (i).init (glyphs, character, x, y);-			}+			item.adjust_scale (); 			-			index++;+			selected_item |= (i == selected);+			item.selected = selected_item;+			+			item.x = x + view_offset_y;+			item.y = y + view_offset_x;+			+			x += full_width;+			+			if (x + full_width >= tab_with) {+				x = OverViewItem.margin;+				y += OverViewItem.full_height ();+			} 		} 		-		foreach (OverViewItem i in visible_items) {-			i.y += view_offset_y;-			i.x += view_offset_x;-		}+		warning (test_b.get_test_time ()); 		+		warning (test3.get_test_time ()); 		warning (test.get_test_time ());-		 		update_scheduled = false; 	} 	@@ -612,7 +650,7 @@ public class OverView : FontDisplay { 			|| this.allocation.height != allocation.height 			|| this.allocation.width == 0) { 			this.allocation = allocation;-			process_update_item_list ();+			process_item_list_update (); 		} 		 		Test test = new Test.time("Overview.draw");diff --git a/libbirdfont/OverViewItem.vala b/libbirdfont/OverViewItem.valaindex fb72d59..548b4ac 100644--- a/libbirdfont/OverViewItem.vala+++ b/libbirdfont/OverViewItem.vala@@ -52,22 +52,25 @@ public class OverViewItem : GLib.Object { 	 	private bool cancel_thumbnail = false; 	-	public OverViewItem (GlyphCollection? glyphs, unichar character, double x, double y) {	-		init (glyphs, character, x, y);+	public OverViewItem () {	 	} -	// this method makes it possible for the overview tab to reuse its items as a speed optimization-	public void init (GlyphCollection? glyphs, unichar character, double x, double y) {-		this.x = x;-		this.y = y;+	public void set_character (unichar character) { 		this.character = character;-		this.glyphs = glyphs;-		this.info = new CharacterInfo (character, glyphs);		--		label = new Text ((!) character.to_string (), 17);		-		truncate_label ();-			-		if (glyphs != null) {+		info = new CharacterInfo (character, glyphs);+		+		if (glyphs == null) {+			label = new Text ();+		} else {+			label = new Text ((!) character.to_string (), 17);		+			truncate_label ();+		}+	}+	+	public void set_glyphs (GlyphCollection? gc) {+		glyphs = gc;+		+		if (glyphs != null) {	 			version_menu = new VersionList ((!) glyphs); 			version_menu.add_glyph_item.connect ((glyph) => { 				((!) glyphs).insert_glyph (glyph, true);@@ -79,10 +82,8 @@ public class OverViewItem : GLib.Object { 				v.update_item_list (); 				GlyphCanvas.redraw (); 			});-		} else {-			version_menu = new VersionList (new GlyphCollection (character, (!) character.to_string ()));-		}-		+		}	+ 		thumbnail_mutex.lock (); 		if (!is_null (thumbnail_queue)) { 			thumbnail_queue.offer (this);@@ -119,12 +120,7 @@ public class OverViewItem : GLib.Object { 				thumbnail_mutex.unlock (); 			 				if (!cancel) {-					IdleSource idle = new IdleSource ();-					idle.set_callback (() => {-						item.draw_background ();-						return false;-					});-					idle.attach (null);+					item.draw_background (); 				} 			} else { 				thumbnail_mutex.lock ();@@ -134,7 +130,11 @@ public class OverViewItem : GLib.Object { 		} 	} -	public void draw_background () { // FIXME: LOCK for Text and thread exit+	public void draw_glyph_from_font () {+		if (glyphs == null) {+			return;+		}+ 		Glyph g; 		Font font; 		double gx, gy;@@ -154,28 +154,58 @@ public class OverViewItem : GLib.Object { 		s = Screen.create_background_surface ((int) width, (int) height - 20); 		c = new Context (s); 		-		if (glyphs != null) {-			font = BirdFont.get_current_font ();-			g = ((!) glyphs).get_current ();-			-			c.save ();-			g.boundaries (out x1, out y1, out x2, out y2);+		g = ((!) glyphs).get_current (); 		-			glyph_width = x2 - x1;-			glyph_height = y2 - y1;-			-			c.save ();-			c.scale (glyph_scale * Screen.get_scale (), glyph_scale * Screen.get_scale ());+		c.save ();+		g.boundaries (out x1, out y1, out x2, out y2);+	+		glyph_width = x2 - x1;+		glyph_height = y2 - y1;+		+		c.save ();+		c.scale (glyph_scale * Screen.get_scale (), glyph_scale * Screen.get_scale ()); -			g.add_help_lines ();-			-			gx = ((w / glyph_scale) - glyph_width) / 2 - g.get_left_side_bearing ();-			gy = (h / glyph_scale) - 25 / glyph_scale;-			-			c.translate (gx - Glyph.xc () - g.get_lsb (), g.get_baseline () + gy - Glyph.yc ());-			-			g.draw_paths (c, color);-			c.restore ();+		g.add_help_lines ();+		+		gx = ((w / glyph_scale) - glyph_width) / 2 - g.get_left_side_bearing ();+		gy = (h / glyph_scale) - 25 / glyph_scale;+		+		c.translate (gx - Glyph.xc () - g.get_lsb (), g.get_baseline () + gy - Glyph.yc ());+		+		g.draw_paths (c, color);+		c.restore ();+		+		cache = s;+		GlyphCanvas.redraw ();+	}++	public void draw_background () { // FIXME: LOCK for Text and thread exit+		Glyph g;+		Font font;+		double gx, gy;+		double x1, x2, y1, y2;+		double scale_box;+		double w, h;+		double glyph_width, glyph_height;+		Surface s;+		Context c;+		Color color = Color.black ();+		+		w = width;+		h = height;+		+		scale_box = width / DEFAULT_WIDTH;++		s = Screen.create_background_surface ((int) width, (int) height - 20);+		c = new Context (s);+		+		if (glyphs != null) { // FIXME: lock+			IdleSource idle_glyph = new IdleSource ();+			idle_glyph.set_callback (() => {+				draw_glyph_from_font ();+				return false;+			});+			idle_glyph.attach (null); 		} else { 			c.scale (Screen.get_scale (), Screen.get_scale ()); 			@@ -185,20 +215,21 @@ public class OverViewItem : GLib.Object { 			Theme.text_color (fallback, "Overview Glyph"); 			fallback.set_text ((!) character.to_string ()); 			double font_size = height * 0.8;+			fallback.set_font_size (font_size); 			gx = (width - fallback.get_extent ()) / 2.0; 			gy = height - 30;-			fallback.set_font_size (font_size); 			fallback.draw_at_baseline (c, gx, gy); 			c.restore ();-		}-		-		IdleSource idle = new IdleSource ();-		idle.set_callback (() => {-			cache = s;-			GlyphCanvas.redraw ();-			return false;-		});-		idle.attach (null);+			+			IdleSource idle = new IdleSource ();+			idle.set_callback (() => {+				cache = s;+				GlyphCanvas.redraw ();+				return false;+			});+			idle.attach (null);+			+		}		 	}  	public static void reset_label () {

Contact

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