The Birdfont Source Code


All Repositories / birdfont.git / blob – RSS feed

BackgroundTool.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/BackgroundTool.vala.
Fix zero length handles
1 /* 2 Copyright (C) 2012 2014 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 BackgroundTool : Tool { 20 21 double begin_x = 0; 22 double begin_y = 0; 23 24 public double img_offset_x = 0; 25 public double img_offset_y = 0; 26 27 public double img_width = 0; 28 public double img_height = 0; 29 30 public double img_scale_x = 0; 31 32 public static double top_limit; 33 public static double bottom_limit; 34 35 bool move_bg; 36 37 static BackgroundImage imported_background; 38 static ImageSurface imported_surface; 39 40 public BackgroundTool (string name) { 41 base (name, t_("Move, resize and rotate background image")); 42 43 top_limit = 0; 44 bottom_limit = 0; 45 46 imported_background = new BackgroundImage (""); 47 48 select_action.connect((self) => { 49 }); 50 51 deselect_action.connect ((self) => { 52 }); 53 54 press_action.connect((self, b, x, y) => { 55 Glyph g = MainWindow.get_current_glyph (); 56 BackgroundImage? bg = g.get_background_image (); 57 BackgroundImage background; 58 59 if (bg == null) { 60 return; 61 } 62 63 background = (!) bg; 64 65 g.store_undo_state (); 66 67 background.handler_press (x, y); 68 69 begin_x = x; 70 begin_y = y; 71 72 img_offset_x = background.img_offset_x; 73 img_offset_y = background.img_offset_y; 74 75 img_scale_x = background.img_scale_x; 76 77 img_width = background.get_img ().get_width () * background.img_scale_x; 78 img_height = background.get_img ().get_height () * background.img_scale_y; 79 80 move_bg = true; 81 }); 82 83 release_action.connect((self, b, x, y) => { 84 Glyph g = MainWindow.get_current_glyph (); 85 BackgroundImage? bg = g.get_background_image (); 86 87 if (bg == null) { 88 return; 89 } 90 91 img_offset_x = ((!)bg).img_offset_x; 92 img_offset_y = ((!)bg).img_offset_y; 93 94 ((!)bg).handler_release (x, y); 95 96 move_bg = false; 97 }); 98 99 move_action.connect((self, x, y) => { 100 move (x, y); 101 }); 102 103 key_press_action.connect ((self, keyval) => { 104 move_bg = true; 105 begin_x = 0; 106 begin_y = 0; 107 108 switch (keyval) { 109 case Key.UP: 110 move (0, -1); 111 break; 112 case Key.DOWN: 113 move (0, 1); 114 break; 115 case Key.LEFT: 116 move (-1, 0); 117 break; 118 case Key.RIGHT: 119 move (1, 0); 120 break; 121 default: 122 break; 123 } 124 125 move_bg = false; 126 }); 127 128 129 draw_action.connect ((self, cairo_context, glyph) => { 130 Glyph g = MainWindow.get_current_glyph (); 131 BackgroundImage? background_image = g.get_background_image (); 132 if (background_image == null) return; 133 134 ((!) background_image).draw_handle (cairo_context, glyph); 135 }); 136 } 137 138 void move (double x, double y) { 139 Glyph g = MainWindow.get_current_glyph (); 140 BackgroundImage? background_image = g.get_background_image (); 141 BackgroundImage bg = (!) background_image; 142 double xscale, yscale, dx, dy, xc, yc; 143 double coordinate_x, coordinate_y; 144 145 if (background_image == null) { 146 return; 147 } 148 149 bg.handler_move (x, y); 150 151 dx = x - begin_x; 152 dy = y - begin_y; 153 154 dx *= 1 / g.view_zoom; 155 dy *= 1 / g.view_zoom; 156 157 dx *= PenTool.precision; 158 dy *= PenTool.precision; 159 160 if (bg.selected_handle == 2) { 161 coordinate_x = Glyph.path_coordinate_x (x); 162 coordinate_y = Glyph.path_coordinate_y (y); 163 bg.set_img_rotation_from_coordinate (coordinate_x, coordinate_y); 164 } 165 166 if (bg.selected_handle == 1) { 167 xscale = img_scale_x * ((img_width - dx) / img_width); 168 yscale = xscale; 169 170 xc = bg.img_middle_x; 171 yc = bg.img_middle_y; 172 173 bg.set_img_scale (xscale, yscale); 174 175 bg.img_middle_x = xc; 176 bg.img_middle_y = yc; 177 } 178 179 if (move_bg && bg.selected_handle <= 0) { 180 bg.set_img_offset (this.img_offset_x + dx, this.img_offset_y + dy); 181 } 182 183 GlyphCanvas.redraw (); 184 } 185 186 public static void load_background_image () { 187 // generate png file if needed and load the image with cairo 188 imported_surface = imported_background.get_img (); 189 190 IdleSource idle = new IdleSource (); 191 idle.set_callback (() => { 192 TabBar tb = MainWindow.get_tab_bar (); 193 Glyph g = MainWindow.get_current_glyph (); 194 195 g.set_background_image (imported_background); 196 imported_background.center_in_glyph (); 197 198 Toolbox.select_tool_by_name ("zoom_background_image"); 199 tb.select_tab_name (g.get_name ()); 200 Toolbox.select_tool_by_name ("cut_background"); 201 202 GlyphCanvas.redraw (); 203 return false; 204 }); 205 idle.attach (null); 206 } 207 208 internal static void import_background_image () { 209 FileChooser fc = new FileChooser (); 210 211 fc.file_selected.connect ((fn) => { 212 BackgroundImage bg; 213 string path; 214 215 if (fn != null) { 216 path = (!) fn; 217 bg = new BackgroundImage (path); 218 imported_background = bg; 219 MainWindow.native_window.load_background_image (); 220 } 221 }); 222 223 MainWindow.file_chooser (t_("Select background image"), fc, FileChooser.LOAD); 224 } 225 } 226 227 } 228