Merge lp:~gaspa/a4/path-refactoring into lp:a4
- path-refactoring
- Merge into trunk
Proposed by
Andrea Gasparini
Status: | Merged |
---|---|
Merged at revision: | 108 |
Proposed branch: | lp:~gaspa/a4/path-refactoring |
Merge into: | lp:a4 |
Diff against target: |
274 lines (+100/-79) 4 files modified
a4lib/app.py (+2/-2) a4lib/editor.py (+82/-71) a4lib/presentation.py (+11/-5) a4lib/presentation_objects.py (+5/-1) |
To merge this branch: | bzr merge lp:~gaspa/a4/path-refactoring |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
A4 Developers | Pending | ||
Review via email: mp+44764@code.launchpad.net |
Commit message
Description of the change
some refactoring for path handling, and some calculations of region properties.
To post a comment you must log in.
lp:~gaspa/a4/path-refactoring
updated
- 113. By Andrea Gasparini
-
show_path does not really hides paths
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === modified file 'a4lib/app.py' | |||
2 | --- a4lib/app.py 2010-12-22 22:55:51 +0000 | |||
3 | +++ a4lib/app.py 2010-12-30 20:33:31 +0000 | |||
4 | @@ -273,8 +273,6 @@ | |||
5 | 273 | 273 | ||
6 | 274 | widget_name = gtk.Buildable.get_name(widget) | 274 | widget_name = gtk.Buildable.get_name(widget) |
7 | 275 | if widget.get_active(): | 275 | if widget.get_active(): |
8 | 276 | if widget_name == 'PathToolbutton': | ||
9 | 277 | self.player.set_show_path(widget.get_active()) | ||
10 | 278 | for i in toggle_modes.keys(): | 276 | for i in toggle_modes.keys(): |
11 | 279 | if i != widget_name: | 277 | if i != widget_name: |
12 | 280 | obj = self.builder.get_object(i) | 278 | obj = self.builder.get_object(i) |
13 | @@ -290,6 +288,8 @@ | |||
14 | 290 | self.player.set_target_image(self._ask_image_dialog()) | 288 | self.player.set_target_image(self._ask_image_dialog()) |
15 | 291 | if not any(self.builder.get_object(i).get_active() for i in toggle_modes.keys()): | 289 | if not any(self.builder.get_object(i).get_active() for i in toggle_modes.keys()): |
16 | 292 | self.player.set_editor_mode() | 290 | self.player.set_editor_mode() |
17 | 291 | path_widget = self.builder.get_object('PathToolbutton') | ||
18 | 292 | self.player.set_show_path(path_widget.get_active()) | ||
19 | 293 | self.drawing_area.queue_draw() | 293 | self.drawing_area.queue_draw() |
20 | 294 | 294 | ||
21 | 295 | def on_drawing_area_expose(self, widget, event): | 295 | def on_drawing_area_expose(self, widget, event): |
22 | 296 | 296 | ||
23 | === modified file 'a4lib/editor.py' | |||
24 | --- a4lib/editor.py 2010-12-22 22:55:51 +0000 | |||
25 | +++ a4lib/editor.py 2010-12-30 20:33:31 +0000 | |||
26 | @@ -18,11 +18,24 @@ | |||
27 | 18 | return obj_dict[name] | 18 | return obj_dict[name] |
28 | 19 | 19 | ||
29 | 20 | 20 | ||
34 | 21 | class Editor(GtkCairoPlayer): | 21 | def cairo_draw_rect(ctx, x0, y0, x1, y1, r, g, b, alpha): |
35 | 22 | 22 | ctx.set_source_rgb(0, 0xff, 0) | |
36 | 23 | def __init__(self, file_name, drawing_area, treeview, force_loading=False): | 23 | ctx.move_to(x0, y0) |
37 | 24 | GtkCairoPlayer.__init__(self, file_name, drawing_area, force_loading) | 24 | ctx.line_to(x1, y0) |
38 | 25 | ctx.line_to(x1, y1) | ||
39 | 26 | ctx.line_to(x0, y1) | ||
40 | 27 | ctx.line_to(x0, y0) | ||
41 | 28 | ctx.set_line_width(0.2) | ||
42 | 29 | ctx.stroke() | ||
43 | 30 | ctx.rectangle(x0, y0, x1 - x0, y1 - y0) | ||
44 | 31 | ctx.set_source_rgba(0, 0, 0.5, 0.50) | ||
45 | 32 | ctx.fill() | ||
46 | 33 | |||
47 | 34 | |||
48 | 35 | class PresentationPathHandler(object): | ||
49 | 36 | def __init__(self, presentation, treeview): | ||
50 | 25 | self.treeview = treeview | 37 | self.treeview = treeview |
51 | 38 | self.presentation = presentation | ||
52 | 26 | self.model = gtk.ListStore(int, str, gtk.gdk.Pixbuf) | 39 | self.model = gtk.ListStore(int, str, gtk.gdk.Pixbuf) |
53 | 27 | 40 | ||
54 | 28 | self.treeview.set_model(self.model) | 41 | self.treeview.set_model(self.model) |
55 | @@ -33,6 +46,46 @@ | |||
56 | 33 | self.treeview.set_item_width(120) | 46 | self.treeview.set_item_width(120) |
57 | 34 | self.treeview.set_size_request(130, -1) | 47 | self.treeview.set_size_request(130, -1) |
58 | 35 | 48 | ||
59 | 49 | def draw_region_on_iconview(self, region, position=0): | ||
60 | 50 | pixbuf_height = abs(int(100 * region.height / region.width)) | ||
61 | 51 | pixbuf = gtk.gdk.Pixbuf(gtk.gdk.COLORSPACE_RGB, True, 8, 100, | ||
62 | 52 | pixbuf_height) | ||
63 | 53 | pix_data = pixbuf.get_pixels_array() | ||
64 | 54 | pixbuf_size = (pixbuf.get_width(), pixbuf.get_height()) | ||
65 | 55 | surface = cairo.ImageSurface.create_for_data(pix_data, cairo.FORMAT_ARGB32, | ||
66 | 56 | pixbuf_size[0], pixbuf_size[1], pixbuf.get_rowstride()) | ||
67 | 57 | cr = cairo.Context(surface) | ||
68 | 58 | region.render(cr, self.presentation, pixbuf_size) | ||
69 | 59 | |||
70 | 60 | self.model.append([position, str(position), pixbuf]) | ||
71 | 61 | |||
72 | 62 | def draw_regions_on_iconview(self, regions): | ||
73 | 63 | for n, region in enumerate(regions): | ||
74 | 64 | self.draw_region_on_iconview(region, n) | ||
75 | 65 | |||
76 | 66 | def highlight_path_region(self, context, region): | ||
77 | 67 | context.save() | ||
78 | 68 | context.translate(region.xc, region.yc) | ||
79 | 69 | context.rotate(region.rotate) | ||
80 | 70 | context.translate(-region.xc, -region.yc) | ||
81 | 71 | x0 = region.xc - region.width / 2 | ||
82 | 72 | y0 = region.yc - region.height / 2 | ||
83 | 73 | x1 = region.xc + region.width / 2 | ||
84 | 74 | y1 = region.yc + region.height / 2 | ||
85 | 75 | cairo_draw_rect(context, x0, y0, x1, y1, 0, 0, 0.5, 0.50) | ||
86 | 76 | context.restore() | ||
87 | 77 | |||
88 | 78 | def render(self, context): | ||
89 | 79 | for i in xrange(0, len(self.presentation.path)): | ||
90 | 80 | region = self.presentation.get_path_region(i) | ||
91 | 81 | self.highlight_path_region(context, region) | ||
92 | 82 | |||
93 | 83 | |||
94 | 84 | class Editor(GtkCairoPlayer): | ||
95 | 85 | |||
96 | 86 | def __init__(self, file_name, drawing_area, treeview, force_loading=False): | ||
97 | 87 | GtkCairoPlayer.__init__(self, file_name, drawing_area, force_loading) | ||
98 | 88 | self.path_handler = PresentationPathHandler(self.presentation, treeview) | ||
99 | 36 | ## used to keep status of mouse actions: | 89 | ## used to keep status of mouse actions: |
100 | 37 | ## value currently used: [None,'start','moving'] | 90 | ## value currently used: [None,'start','moving'] |
101 | 38 | self.action_status = None | 91 | self.action_status = None |
102 | @@ -46,9 +99,8 @@ | |||
103 | 46 | self.current_object = None | 99 | self.current_object = None |
104 | 47 | self.target_filename = None | 100 | self.target_filename = None |
105 | 48 | 101 | ||
109 | 49 | for i in xrange(0, len(self.presentation.path)): | 102 | ph = self.path_handler |
110 | 50 | region = self.presentation.get_path_region(i) | 103 | ph.draw_regions_on_iconview(self.presentation.get_path_regions()) |
108 | 51 | self.draw_region_on_iconview(region, i) | ||
111 | 52 | 104 | ||
112 | 53 | def set_show_path(self, flag=True): | 105 | def set_show_path(self, flag=True): |
113 | 54 | self.show_path = flag | 106 | self.show_path = flag |
114 | @@ -124,36 +176,16 @@ | |||
115 | 124 | self.action_status = None | 176 | self.action_status = None |
116 | 125 | return True | 177 | return True |
117 | 126 | 178 | ||
148 | 127 | def draw_selection_box(self, context, region=None): | 179 | def draw_selection_box(self, context): |
149 | 128 | context.save() | 180 | win_size = self.area.window.get_size() |
150 | 129 | if not region: | 181 | cr = self.current_region |
151 | 130 | context.set_matrix(cairo.Matrix(1, 0, 0, 1, 0, 0)) | 182 | x0 = self.selection_start_position[0] |
152 | 131 | x0 = self.selection_start_position[0] | 183 | y0 = self.selection_start_position[1] |
153 | 132 | y0 = self.selection_start_position[1] | 184 | x1 = self.mouse_position[0] |
154 | 133 | x1 = self.mouse_position[0] | 185 | y1 = self.mouse_position[1] |
155 | 134 | y1 = self.mouse_position[1] | 186 | x0, y0 = cr.get_point_from_window_coordinates(win_size, (x0, y0)) |
156 | 135 | else: | 187 | x1, y1 = cr.get_point_from_window_coordinates(win_size, (x1, y1)) |
157 | 136 | context.translate(region.xc, region.yc) | 188 | cairo_draw_rect(context, x0, y0, x1, y1, 0, 0, 0.5, 0.50) |
128 | 137 | context.rotate(region.rotate) | ||
129 | 138 | context.translate(-region.xc, -region.yc) | ||
130 | 139 | x0 = region.xc - region.width / 2 | ||
131 | 140 | y0 = region.yc - region.height / 2 | ||
132 | 141 | x1 = region.xc + region.width / 2 | ||
133 | 142 | y1 = region.yc + region.height / 2 | ||
134 | 143 | |||
135 | 144 | context.set_source_rgb(0, 0xff, 0) | ||
136 | 145 | context.move_to(x0, y0) | ||
137 | 146 | context.line_to(x1, y0) | ||
138 | 147 | context.line_to(x1, y1) | ||
139 | 148 | context.line_to(x0, y1) | ||
140 | 149 | context.line_to(x0, y0) | ||
141 | 150 | context.set_line_width(0.2) | ||
142 | 151 | context.stroke() | ||
143 | 152 | |||
144 | 153 | context.rectangle(x0, y0, x1 - x0, y1 - y0) | ||
145 | 154 | context.set_source_rgba(0, 0, 0.5, 0.50) | ||
146 | 155 | context.fill() | ||
147 | 156 | context.restore() | ||
158 | 157 | 189 | ||
159 | 158 | def render(self, context): | 190 | def render(self, context): |
160 | 159 | # render a transparent box (should indicate the selection) | 191 | # render a transparent box (should indicate the selection) |
161 | @@ -161,47 +193,26 @@ | |||
162 | 161 | # render an icon for rotating the whole image. | 193 | # render an icon for rotating the whole image. |
163 | 162 | GtkCairoPlayer.render(self, context) | 194 | GtkCairoPlayer.render(self, context) |
164 | 163 | if self.show_path: | 195 | if self.show_path: |
168 | 164 | for i in xrange(0, len(self.presentation.path)): | 196 | ## render the path over the presentation |
169 | 165 | region = self.presentation.get_path_region(i) | 197 | self.path_handler.render(context) |
170 | 166 | self.draw_selection_box(context, region) | 198 | ## render the selection (TODO: not only for path) |
171 | 167 | if self.editor_mode == 'path' and self.action_status: | 199 | if self.editor_mode == 'path' and self.action_status: |
172 | 168 | self.draw_selection_box(context) | 200 | self.draw_selection_box(context) |
173 | 169 | 201 | ||
174 | 170 | def add_treeview_icon(self, rect=None): | 202 | def add_treeview_icon(self, rect=None): |
176 | 171 | ## * trasforma rect in Regione | 203 | ## convert a rect into a Region() |
177 | 172 | win_size = self.area.window.get_size() | 204 | win_size = self.area.window.get_size() |
193 | 173 | scale = self.current_region.get_window_scale_factor(win_size) | 205 | |
194 | 174 | translate = self.current_region.get_window_fit_vector(win_size) | 206 | cr = self.current_region |
195 | 175 | translate = translate[0] / 2.0, translate[1] / 2.0 | 207 | rect2 = (cr.get_point_from_window_coordinates(win_size, rect[0]), |
196 | 176 | rect2 = (((rect[0][0] - translate[0]) / scale, | 208 | cr.get_point_from_window_coordinates(win_size, rect[1])) |
197 | 177 | (rect[0][1] - translate[1]) / scale), | 209 | xc = (rect2[0][0] + rect2[1][0]) / 2 |
198 | 178 | ((rect[1][0] - translate[0]) / scale, | 210 | yc = (rect2[0][1] + rect2[1][1]) / 2 |
199 | 179 | (rect[1][1] - translate[1]) / scale)) | 211 | region = Region(xc, yc, |
185 | 180 | xc = (rect2[0][0] + rect2[1][0]) / 2 - self.current_region.width / 2 | ||
186 | 181 | yc = (rect2[0][1] + rect2[1][1]) / 2 - self.current_region.height / 2 | ||
187 | 182 | r = self.current_region.rotate | ||
188 | 183 | xc1 = math.cos(r) * xc - math.sin(r) * yc | ||
189 | 184 | yc1 = math.sin(r) * xc + math.cos(r) * yc | ||
190 | 185 | region = Region( | ||
191 | 186 | self.current_region.xc + xc1, | ||
192 | 187 | self.current_region.yc + yc1, | ||
200 | 188 | (rect2[1][0] - rect2[0][0]), | 212 | (rect2[1][0] - rect2[0][0]), |
201 | 189 | (rect2[1][1] - rect2[0][1]), | 213 | (rect2[1][1] - rect2[0][1]), |
203 | 190 | self.current_region.rotate) | 214 | cr.rotate) |
204 | 191 | ## * metti la regione in lista | 215 | ## * metti la regione in lista |
205 | 192 | self.presentation.path.append(region) | 216 | self.presentation.path.append(region) |
206 | 193 | ## * usa la regione per la pixbuf. | 217 | ## * usa la regione per la pixbuf. |
221 | 194 | self.draw_region_on_iconview(region, len(self.presentation.path) - 1) | 218 | self.path_handler.draw_region_on_iconview(region, len(self.presentation.path) - 1) |
208 | 195 | |||
209 | 196 | def draw_region_on_iconview(self, region, position=0): | ||
210 | 197 | pixbuf_height = abs(int(100 * region.height / region.width)) | ||
211 | 198 | pixbuf = gtk.gdk.Pixbuf(gtk.gdk.COLORSPACE_RGB, True, 8, 100, | ||
212 | 199 | pixbuf_height) | ||
213 | 200 | pix_data = pixbuf.get_pixels_array() | ||
214 | 201 | pixbuf_size = (pixbuf.get_width(), pixbuf.get_height()) | ||
215 | 202 | surface = cairo.ImageSurface.create_for_data(pix_data, cairo.FORMAT_ARGB32, | ||
216 | 203 | pixbuf_size[0], pixbuf_size[1], pixbuf.get_rowstride()) | ||
217 | 204 | cr = cairo.Context(surface) | ||
218 | 205 | region.render(cr, self.presentation, pixbuf_size) | ||
219 | 206 | |||
220 | 207 | self.model.append([position, str(position), pixbuf]) | ||
222 | 208 | 219 | ||
223 | === modified file 'a4lib/presentation.py' | |||
224 | --- a4lib/presentation.py 2010-12-13 13:56:31 +0000 | |||
225 | +++ a4lib/presentation.py 2010-12-30 20:33:31 +0000 | |||
226 | @@ -123,13 +123,19 @@ | |||
227 | 123 | out_file = open(self.file_name, 'w') | 123 | out_file = open(self.file_name, 'w') |
228 | 124 | out_file.write(etree.tostring(self.svgtree, pretty_print=True)) | 124 | out_file.write(etree.tostring(self.svgtree, pretty_print=True)) |
229 | 125 | 125 | ||
230 | 126 | def _get_region_from_path(self, path_element): | ||
231 | 127 | if isinstance(path_element, Region): | ||
232 | 128 | return path_element | ||
233 | 129 | props = self.get_item_properties_by_id(path_element.id) | ||
234 | 130 | p = Region.from_obj_props(props) | ||
235 | 131 | return p | ||
236 | 132 | |||
237 | 126 | def get_path_region(self, index): | 133 | def get_path_region(self, index): |
238 | 127 | a = self.path[index] | 134 | a = self.path[index] |
244 | 128 | if isinstance(a, Region): | 135 | return self._get_region_from_path(a) |
245 | 129 | return a | 136 | |
246 | 130 | props = self.get_item_properties_by_id(a.id) | 137 | def get_path_regions(self): |
247 | 131 | p = Region.from_obj_props(props) | 138 | return [self._get_region_from_path(a) for a in self.path] |
243 | 132 | return p | ||
248 | 133 | 139 | ||
249 | 134 | def _handle_transform(self, target_element=None): | 140 | def _handle_transform(self, target_element=None): |
250 | 135 | """Handle SVG transform tags and build a list of tranformations.""" | 141 | """Handle SVG transform tags and build a list of tranformations.""" |
251 | 136 | 142 | ||
252 | === modified file 'a4lib/presentation_objects.py' | |||
253 | --- a4lib/presentation_objects.py 2010-12-22 22:55:51 +0000 | |||
254 | +++ a4lib/presentation_objects.py 2010-12-30 20:33:31 +0000 | |||
255 | @@ -24,6 +24,10 @@ | |||
256 | 24 | self.element.attrib[key] = str(piuprops[key]) | 24 | self.element.attrib[key] = str(piuprops[key]) |
257 | 25 | 25 | ||
258 | 26 | @property | 26 | @property |
259 | 27 | def get_position(self): | ||
260 | 28 | return self.element.attrib['x'], self.element.attrib['y'] | ||
261 | 29 | |||
262 | 30 | @property | ||
263 | 27 | def get_id(self): | 31 | def get_id(self): |
264 | 28 | return self.element.attrib['id'] | 32 | return self.element.attrib['id'] |
265 | 29 | 33 | ||
266 | @@ -38,7 +42,7 @@ | |||
267 | 38 | yc = float(self.element.attrib['y']) | 42 | yc = float(self.element.attrib['y']) |
268 | 39 | xc1 = math.cos(-rotate) * xc - math.sin(-rotate) * yc | 43 | xc1 = math.cos(-rotate) * xc - math.sin(-rotate) * yc |
269 | 40 | yc1 = math.sin(-rotate) * xc + math.cos(-rotate) * yc | 44 | yc1 = math.sin(-rotate) * xc + math.cos(-rotate) * yc |
271 | 41 | self.element.attrib['transform'] = ("rotate(%s)" % str(math.degrees(rotate))) + \ | 45 | self.element.attrib['transform'] = ("rotate(%s)" % str(math.degrees(rotate))) + \ |
272 | 42 | (" translate(%s,%s)" % (xc1 - xc, yc1 - yc)) | 46 | (" translate(%s,%s)" % (xc1 - xc, yc1 - yc)) |
273 | 43 | 47 | ||
274 | 44 | def set_size(self, width, height): | 48 | def set_size(self, width, height): |