The Birdfont Source Code


All Repositories / birdfont.git / blob – RSS feed

OverviewTools.vala in libbirdfont

This file is a part of the Birdfont project.

Contributing

Send patches or pull requests to johan.mattsson.m@gmail.com.
Clone this repository: git clone https://github.com/johanmattssonm/birdfont.git

Revisions

View the latest version of libbirdfont/OverviewTools.vala.
Update overview glyphs after transformation is applied
1 /* 2 Copyright (C) 2014 2015 Johan Mattsson 3 4 This library is free software; you can redistribute it and/or modify 5 it under the terms of the GNU Lesser General Public License as 6 published by the Free Software Foundation; either version 3 of the 7 License, or (at your option) any later version. 8 9 This library is distributed in the hope that it will be useful, but 10 WITHOUT ANY WARRANTY; without even the implied warranty of 11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 Lesser General Public License for more details. 13 */ 14 15 using Cairo; 16 17 namespace BirdFont { 18 19 public class OverviewTools : ToolCollection { 20 21 static LabelTool all_glyphs; 22 static LabelTool default_glyphs; 23 static LabelTool unicode; 24 25 static Gee.ArrayList<LabelTool> custom_character_sets; 26 27 public static Gee.ArrayList<Expander> expanders; 28 public ZoomBar zoom_bar; 29 30 public static Expander zoom_expander; 31 32 public static SpinButton skew; 33 public static SpinButton resize; 34 35 public static double current_master_size; 36 37 public OverviewTools () { 38 Expander font_name = new Expander (); 39 Expander character_sets = new Expander (t_("Character Sets")); 40 Expander zoom_expander = new Expander (t_("Zoom")); 41 Expander transform_expander = new Expander (t_("Transform")); 42 Expander glyph_expander = new Expander (t_("Glyph")); 43 Expander multi_master = new Expander (t_("Multi-Master")); 44 45 expanders = new Gee.ArrayList<Expander> (); 46 custom_character_sets = new Gee.ArrayList<LabelTool> (); 47 48 font_name.add_tool (new FontName ()); 49 50 zoom_bar = new ZoomBar (); 51 zoom_bar.new_zoom.connect ((z) => { 52 get_overview ().set_zoom (z); 53 }); 54 zoom_expander.add_tool (zoom_bar); 55 56 all_glyphs = new LabelTool (t_("All Glyphs")); 57 all_glyphs.has_counter = true; 58 all_glyphs.select_action.connect ((self) => { 59 OverView overview = get_overview (); 60 overview.display_all_available_glyphs (); 61 update_overview_characterset (overview); 62 FontDisplay.dirty_scrollbar = true; 63 }); 64 character_sets.add_tool (all_glyphs); 65 66 default_glyphs = new LabelTool (t_("Default")); 67 default_glyphs.has_counter = true; 68 default_glyphs.select_action.connect ((self) => { 69 OverView overview = get_overview (); 70 GlyphRange gr = new GlyphRange (); 71 DefaultCharacterSet.use_default_range (gr); 72 overview.set_current_glyph_range (gr); 73 update_overview_characterset (overview); 74 FontDisplay.dirty_scrollbar = true; 75 }); 76 character_sets.add_tool (default_glyphs); 77 78 unicode = new LabelTool (t_("Unicode")); 79 unicode.has_counter = true; 80 unicode.select_action.connect ((self) => { 81 OverView overview = get_overview (); 82 GlyphRange gr = new GlyphRange (); 83 DefaultCharacterSet.use_full_unicode_range (gr); 84 overview.set_current_glyph_range (gr); 85 update_overview_characterset (overview); 86 FontDisplay.dirty_scrollbar = true; 87 }); 88 character_sets.add_tool (unicode); 89 90 character_sets.set_persistent (true); 91 character_sets.set_unique (false); 92 93 skew = new SpinButton ("skew_overview", t_("Skew")); 94 skew.set_big_number (true); 95 skew.set_int_value ("0.000"); 96 skew.set_int_step (1); 97 skew.set_min (-100); 98 skew.set_max (100); 99 skew.show_icon (true); 100 skew.set_persistent (false); 101 skew.new_value_action.connect ((self) => { 102 resize.set_value_round (100, false, false); 103 }); 104 transform_expander.add_tool (skew); 105 106 resize = new SpinButton ("resize_overview", t_("Resize")); 107 resize.set_big_number (true); 108 resize.set_int_value ("0.000"); 109 resize.set_int_step (1); 110 resize.set_min (0); 111 resize.set_max (300); 112 resize.show_icon (true); 113 resize.set_persistent (false); 114 resize.new_value_action.connect ((self) => { 115 skew.set_value_round (0, false, false); 116 }); 117 transform_expander.add_tool (resize); 118 119 Tool transform = new Tool ("transform", t_("Transform")); 120 transform.select_action.connect ((self) => { 121 FontSettings fs = BirdFont.get_current_font ().settings; 122 123 fs.set_setting ("skew_overview", @"$(skew.get_value ())"); 124 transform.selected = false; 125 126 process_transform (); 127 128 BirdFont.get_current_font ().touch (); 129 }); 130 transform.selected = false; 131 transform.set_persistent (false); 132 transform_expander.add_tool (transform); 133 134 Tool alternate = new Tool ("alternate", t_("Create alternate")); 135 alternate.select_action.connect (add_new_alternate); 136 glyph_expander.add_tool (alternate); 137 138 Tool curve_orientation = new Tool ("curve_orientation", t_("Set curve orientation")); 139 curve_orientation.select_action.connect ((self) => { 140 Task t = new Task (fix_curve_orientation); 141 142 MainWindow.run_blocking_task (t); 143 144 IdleSource idle = new IdleSource (); 145 idle.set_callback (() => { 146 self.set_selected (false); 147 BirdFont.get_current_font ().touch (); 148 return false; 149 }); 150 idle.attach (null); 151 }); 152 glyph_expander.add_tool (curve_orientation); 153 154 Tool search_glyph = new Tool ("search", t_("Search")); 155 search_glyph.select_action.connect (search_for_glyph); 156 glyph_expander.add_tool (search_glyph); 157 158 SpinButton master_size; 159 current_master_size = 0; 160 master_size = new SpinButton ("master_size", t_("Master Size")); /// Master refers to a glyph master in a multi-master font. 161 master_size.set_big_number (false); 162 master_size.set_int_value ("0.000"); 163 master_size.set_int_step (1); 164 master_size.set_min (-1); 165 master_size.set_max (1); 166 master_size.show_icon (true); 167 master_size.set_persistent (false); 168 master_size.new_value_action.connect ((self) => { 169 current_master_size = self.get_value (); 170 MainWindow.get_overview ().update_item_list (); 171 GlyphCanvas.redraw (); 172 }); 173 multi_master.add_tool (master_size); 174 175 Tool create_new_master = new Tool ("new_master", t_("Create new master font")); /// Master is a master in a multi-master font. 176 create_new_master.select_action.connect (create_master); 177 multi_master.add_tool (create_new_master); 178 179 expanders.add (font_name); 180 expanders.add (zoom_expander); 181 expanders.add (character_sets); 182 expanders.add (transform_expander); 183 expanders.add (glyph_expander); 184 185 if (BirdFont.has_argument ("--test")) { 186 expanders.add (multi_master); 187 } 188 } 189 190 void create_master () { 191 Font font = BirdFont.get_current_font (); 192 int i = 0; 193 GlyphCollection glyph_collection; 194 GlyphCollection? gc = font.get_glyph_collection_index (i); 195 Glyph g; 196 197 while (gc != null) { 198 glyph_collection = (!) gc; 199 200 // FIXME: MASTER NAME 201 GlyphMaster master = new GlyphMaster.for_id("Master 2"); 202 g = glyph_collection.get_interpolated (current_master_size); 203 master.add_glyph(g); 204 glyph_collection.add_master (master); 205 glyph_collection.set_selected_master (master); 206 207 i++; 208 gc = font.get_glyph_collection_index (i); 209 } 210 211 MainWindow.get_overview ().update_item_list (); 212 GlyphCanvas.redraw (); 213 } 214 215 void fix_curve_orientation () { 216 OverView o; 217 Glyph g; 218 OverView.OverViewUndoItem ui; 219 220 o = get_overview (); 221 ui = new OverView.OverViewUndoItem (); 222 223 Font f = BirdFont.get_current_font (); 224 ui.alternate_sets = f.alternates.copy (); 225 226 foreach (GlyphCollection gc in o.selected_items) { 227 if (gc.length () > 0) { 228 g = gc.get_current (); 229 ui.glyphs.add (gc.copy_deep ()); 230 g.add_help_lines (); 231 g.fix_curve_orientation (); 232 } 233 } 234 235 o.undo_items.add (ui); 236 GlyphCanvas.redraw (); 237 } 238 239 public void search_for_glyph (Tool tool) { 240 tool.set_selected (false); 241 OverView.search (); 242 } 243 244 public void add_new_alternate (Tool tool) { 245 OverView o = MainWindow.get_overview (); 246 OverViewItem oi = o.selected_item; 247 GlyphCollection gc; 248 249 tool.set_selected (false); 250 251 if (oi.glyphs == null || ((!) oi.glyphs).is_unassigned ()) { 252 return; 253 } 254 255 gc = (!) oi.glyphs; 256 MainWindow.tabs.add_tab (new OtfFeatureTable (gc)); 257 } 258 259 public void process_transform () { 260 OverView o; 261 Glyph g; 262 OverView.OverViewUndoItem ui; 263 264 o = get_overview (); 265 ui = new OverView.OverViewUndoItem (); 266 267 Font f = BirdFont.get_current_font (); 268 ui.alternate_sets = f.alternates.copy (); 269 270 foreach (GlyphCollection gc in o.selected_items) { 271 if (gc.length () > 0) { 272 g = gc.get_current (); 273 ui.glyphs.add (gc.copy_deep ()); 274 g.add_help_lines (); 275 276 if (skew.get_value () != 0) { 277 DrawingTools.resize_tool.skew_glyph (g, -skew.get_value (), 0, false); 278 } 279 280 if (resize.get_value () != 100) { 281 double scale = resize.get_value () / 100; 282 DrawingTools.resize_tool.resize_glyph (g, scale, scale, false); 283 } 284 } 285 } 286 287 o.undo_items.add (ui); 288 289 MainWindow.get_overview ().update_item_list (); 290 GlyphCanvas.redraw (); 291 } 292 293 public OverView get_overview () { 294 FontDisplay fd = MainWindow.get_current_display (); 295 296 if (fd is OverView || fd is GlyphSelection) { 297 return (OverView) fd; 298 } 299 300 warning ("Current tab is not overview."); 301 302 return new OverView (); 303 } 304 305 public static void show_all_available_characters () { 306 all_glyphs.select_action (all_glyphs); 307 } 308 309 public static void update_overview_characterset (OverView? tab = null) { 310 GlyphRange gr; 311 uint size; 312 OverView overview; 313 Font font; 314 315 // All characters including .notdef 316 font = BirdFont.get_current_font (); 317 size = font.length (); 318 319 if (!font.has_glyph (".notdef")) { 320 size++; 321 } 322 323 all_glyphs.number = get_display_value (size); 324 325 // Default 326 gr = new GlyphRange (); 327 DefaultCharacterSet.use_default_range (gr); 328 size = gr.get_length (); 329 default_glyphs.number = get_display_value (size); 330 331 // Unicode 332 gr = new GlyphRange (); 333 DefaultCharacterSet.use_full_unicode_range (gr); 334 size = gr.get_length (); 335 unicode.number = get_display_value (size); 336 337 overview = (tab == null) ? MainWindow.get_overview () : (!) tab; 338 339 // set selected item 340 all_glyphs.set_selected (false); 341 default_glyphs.set_selected (false); 342 unicode.set_selected (false); 343 344 if (overview.all_available) { 345 all_glyphs.set_selected (true); 346 } else if (overview.glyph_range.name == "Default") { 347 default_glyphs.set_selected (true); 348 } else if (overview.glyph_range.name == "Unicode") { 349 unicode.set_selected (true); 350 } 351 352 Toolbox.redraw_tool_box (); 353 } 354 355 static string get_display_value (uint size) { 356 double k; 357 string display_size; 358 359 if (size >= 1000) { 360 k = size / 1000.0; 361 size = (uint) Math.rint (k); 362 display_size = @"$(size)k"; 363 } else { 364 display_size = @"$(size)"; 365 } 366 367 return display_size; 368 } 369 370 public override Gee.ArrayList<Expander> get_expanders () { 371 return expanders; 372 } 373 374 public override Gee.ArrayList<string> get_displays () { 375 Gee.ArrayList<string> d = new Gee.ArrayList<string> (); 376 d.add ("Overview"); 377 return d; 378 } 379 } 380 381 } 382