Merge lp:~gtg-user/gtg/plugins-preferences-separation into lp:~gtg/gtg/old-trunk
- plugins-preferences-separation
- Merge into old-trunk
Status: | Merged | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Merged at revision: | 1193 | ||||||||||||
Proposed branch: | lp:~gtg-user/gtg/plugins-preferences-separation | ||||||||||||
Merge into: | lp:~gtg/gtg/old-trunk | ||||||||||||
Diff against target: |
1996 lines (+850/-866) 10 files modified
GTG/gtk/__init__.py (+1/-0) GTG/gtk/backends_dialog.glade (+0/-1) GTG/gtk/backends_dialog/__init__.py (+2/-2) GTG/gtk/browser/browser.py (+7/-6) GTG/gtk/browser/taskbrowser.glade (+27/-12) GTG/gtk/manager.py (+8/-5) GTG/gtk/plugins.glade (+227/-0) GTG/gtk/plugins.py (+322/-0) GTG/gtk/preferences.glade (+154/-427) GTG/gtk/preferences.py (+102/-413) |
||||||||||||
To merge this branch: | bzr merge lp:~gtg-user/gtg/plugins-preferences-separation | ||||||||||||
Related bugs: |
|
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Bertrand Rousseau (community) | run | Approve | |
Review via email: mp+108265@code.launchpad.net |
Commit message
Description of the change
Move Plugins dialog into Edit menu. I also cleaned the code a little bit. A little problem is that moving Plugins into a standalone dialogs from Gtk.Notebook creates weird looking dialogs. See the screenshots: http://
Bertrand Rousseau (bertrand-rousseau) wrote : | # |
- 1188. By Izidor Matušov
-
Small GLADE tweaks
- 1189. By Izidor Matušov
-
Solve bug #1008246: Add enter accelerator in Task menu
Izidor Matušov (izidor) wrote : | # |
I've made your suggested fixes. I also made the caption of plugins dialog to be a little bigger and added one to preferences dialog as well.
I removed CTRL+e accelerator and added "Return" accelerator to Edit task in menu. gtk.accelerator
Looking forward to further suggestions :)
Bertrand Rousseau (bertrand-rousseau) wrote : | # |
Hi, it looks better! But I have still some remarks (nitpicking, as always ;-) ):
- I think we're better off getting rid of the "Preferences" and "Available plugins" caption. They're redundant with the window title, it creates clutter.
- If the preference dialog looks too simple without caption, then maybe putting some kind of frame can provide a better look. Maybe it's even possible to actually still use a notebook but not displaying the tab (since there would be only one then).
- 1190. By Izidor Matušov
-
More GLADE tweaks
Izidor Matušov (izidor) wrote : | # |
I love nitpicking :) Few more changes to nitpick :)
Bertrand Rousseau (bertrand-rousseau) wrote : | # |
Good job!
Ok, there is maybe a bit too much padding around the frame in the
preference window now (3 px should be enough).
If you change that, you get my approval for merging!
Bertrand
On Mon, Jun 4, 2012 at 11:03 PM, Izidor Matušov
<email address hidden> wrote:
> I love nitpicking :) Few more changes to nitpick :)
> --
> https:/
> You are reviewing the proposed merge of lp:~gtg-user/gtg/plugins-preferences-separation into lp:gtg.
--
Bertrand Rousseau
- 1191. By Izidor Matušov
-
Merging the current trunk
- 1192. By Izidor Matušov
-
Set the title of edit dialogs on fly because of -t option
- 1193. By Izidor Matušov
-
Decreased the padding in preference window
Izidor Matušov (izidor) wrote : | # |
-t option from the trunk now works for dialogs from Edit menu. I also set 3px padding. What should be done more?
Bertrand Rousseau (bertrand-rousseau) wrote : | # |
Until I know more about how we're supposed to provide preferences in GNOME 3.x, that'll be ok! I approve!
Preview Diff
1 | === modified file 'GTG/gtk/__init__.py' |
2 | --- GTG/gtk/__init__.py 2012-03-17 02:20:46 +0000 |
3 | +++ GTG/gtk/__init__.py 2012-06-07 15:29:21 +0000 |
4 | @@ -26,4 +26,5 @@ |
5 | current_rep = os.path.dirname(os.path.abspath(__file__)) |
6 | DELETE_GLADE_FILE = os.path.join(current_rep, "deletion.glade") |
7 | PREFERENCES_GLADE_FILE = os.path.join(current_rep, "preferences.glade") |
8 | + PLUGINS_GLADE_FILE = os.path.join(current_rep, "plugins.glade") |
9 | BACKENDS_GLADE_FILE = os.path.join(current_rep, "backends_dialog.glade") |
10 | |
11 | === modified file 'GTG/gtk/backends_dialog.glade' |
12 | --- GTG/gtk/backends_dialog.glade 2012-05-25 16:57:38 +0000 |
13 | +++ GTG/gtk/backends_dialog.glade 2012-06-07 15:29:21 +0000 |
14 | @@ -4,7 +4,6 @@ |
15 | <!-- interface-naming-policy project-wide --> |
16 | <object class="GtkWindow" id="backends_dialog"> |
17 | <property name="window_position">mouse</property> |
18 | - <property name="title" translatable="yes">Synchronization Services - Getting Things GNOME!</property> |
19 | <signal name="delete_event" handler="on_BackendsDialog_delete_event"/> |
20 | <child> |
21 | <object class="GtkAlignment" id="alignment1"> |
22 | |
23 | === modified file 'GTG/gtk/backends_dialog/__init__.py' |
24 | --- GTG/gtk/backends_dialog/__init__.py 2012-05-25 16:57:38 +0000 |
25 | +++ GTG/gtk/backends_dialog/__init__.py 2012-06-07 15:29:21 +0000 |
26 | @@ -37,7 +37,7 @@ |
27 | from GTG.tools.logger import Log |
28 | from GTG import _ |
29 | from GTG.backends.genericbackend import GenericBackend |
30 | - |
31 | +from GTG import info |
32 | |
33 | |
34 | class BackendsDialog(object): |
35 | @@ -48,7 +48,6 @@ |
36 | - the backend adding view |
37 | ''' |
38 | |
39 | - |
40 | def __init__(self, req): |
41 | ''' |
42 | Initializes the gtk objects and signals. |
43 | @@ -58,6 +57,7 @@ |
44 | self._configure_icon_theme() |
45 | builder = gtk.Builder() |
46 | self._load_widgets_from_glade(builder) |
47 | + self.dialog.set_title(_("Synchronization Services - %s" % info.NAME)) |
48 | self._create_widgets_for_add_panel() |
49 | self._create_widgets_for_configure_panel() |
50 | self._setup_signal_connections(builder) |
51 | |
52 | === modified file 'GTG/gtk/browser/browser.py' |
53 | --- GTG/gtk/browser/browser.py 2012-06-07 11:52:38 +0000 |
54 | +++ GTG/gtk/browser/browser.py 2012-06-07 15:29:21 +0000 |
55 | @@ -339,6 +339,8 @@ |
56 | lambda w: openurl(info.REPORT_BUG_URL), |
57 | "on_preferences_activate": |
58 | self.open_preferences, |
59 | + "on_edit_plugins_activate": |
60 | + self.open_plugins, |
61 | "on_edit_backends_activate": |
62 | self.open_edit_backends, |
63 | } |
64 | @@ -388,18 +390,14 @@ |
65 | self._add_accelerator_for_widget(agr, "new_task_mi", "<Control>n") |
66 | self._add_accelerator_for_widget(agr, "new_subtask_mi", |
67 | "<Control><Shift>n") |
68 | + self._add_accelerator_for_widget(agr, "edit_mi", "Return") |
69 | self._add_accelerator_for_widget(agr, "done_mi", "<Control>d") |
70 | self._add_accelerator_for_widget(agr, "dismiss_mi", "<Control>i") |
71 | - self._add_accelerator_for_widget(agr, "delete_mi", "Cancel") |
72 | + self._add_accelerator_for_widget(agr, "delete_mi", "Delete") |
73 | self._add_accelerator_for_widget(agr, "tcm_modifytags", "<Control>t") |
74 | self._add_accelerator_for_widget(agr, "view_closed", "<Control>F9") |
75 | self._add_accelerator_for_widget(agr, "online_help", "F1") |
76 | |
77 | - edit_button = self.builder.get_object("edit_b") |
78 | - key, mod = gtk.accelerator_parse("<Control>e") |
79 | - edit_button.add_accelerator("clicked", agr, key, mod, |
80 | - gtk.ACCEL_VISIBLE) |
81 | - |
82 | quickadd_field = self.builder.get_object("quickadd_field") |
83 | key, mod = gtk.accelerator_parse("<Control>l") |
84 | quickadd_field.add_accelerator("grab-focus", agr, key, mod, |
85 | @@ -408,6 +406,9 @@ |
86 | ### HELPER FUNCTIONS ######################################################## |
87 | def open_preferences(self, widget): |
88 | self.vmanager.open_preferences(self.config) |
89 | + |
90 | + def open_plugins(self, widget): |
91 | + self.vmanager.configure_plugins() |
92 | |
93 | def open_edit_backends(self, widget): |
94 | self.vmanager.open_edit_backends() |
95 | |
96 | === modified file 'GTG/gtk/browser/taskbrowser.glade' |
97 | --- GTG/gtk/browser/taskbrowser.glade 2012-05-27 18:20:57 +0000 |
98 | +++ GTG/gtk/browser/taskbrowser.glade 2012-06-07 15:29:21 +0000 |
99 | @@ -175,6 +175,32 @@ |
100 | </object> |
101 | </child> |
102 | <child> |
103 | + <object class="GtkMenuItem" id="plugins_mi"> |
104 | + <property name="visible">True</property> |
105 | + <property name="can_focus">False</property> |
106 | + <property name="use_action_appearance">False</property> |
107 | + <property name="label">P_lugins</property> |
108 | + <property name="use_underline">True</property> |
109 | + <signal name="activate" handler="on_edit_plugins_activate" swapped="no"/> |
110 | + </object> |
111 | + </child> |
112 | + <child> |
113 | + <object class="GtkMenuItem" id="backends_mi"> |
114 | + <property name="visible">True</property> |
115 | + <property name="can_focus">False</property> |
116 | + <property name="use_action_appearance">False</property> |
117 | + <property name="label">_Synchronization Services</property> |
118 | + <property name="use_underline">True</property> |
119 | + <signal name="activate" handler="on_edit_backends_activate" swapped="no"/> |
120 | + </object> |
121 | + </child> |
122 | + <child> |
123 | + <object class="GtkSeparatorMenuItem" id="separator_4"> |
124 | + <property name="visible">True</property> |
125 | + <property name="can_focus">False</property> |
126 | + </object> |
127 | + </child> |
128 | + <child> |
129 | <object class="GtkImageMenuItem" id="edit_preferences_mi"> |
130 | <property name="label">gtk-preferences</property> |
131 | <property name="visible">True</property> |
132 | @@ -186,15 +212,6 @@ |
133 | <signal name="activate" handler="on_preferences_activate" swapped="no"/> |
134 | </object> |
135 | </child> |
136 | - <child> |
137 | - <object class="GtkMenuItem" id="backends_mi"> |
138 | - <property name="visible">True</property> |
139 | - <property name="can_focus">False</property> |
140 | - <property name="use_action_appearance">False</property> |
141 | - <property name="label">Setup Sync. Services</property> |
142 | - <signal name="activate" handler="on_edit_backends_activate" swapped="no"/> |
143 | - </object> |
144 | - </child> |
145 | </object> |
146 | </child> |
147 | </object> |
148 | @@ -221,7 +238,7 @@ |
149 | </object> |
150 | </child> |
151 | <child> |
152 | - <object class="GtkSeparatorMenuItem" id="separator_4"> |
153 | + <object class="GtkSeparatorMenuItem" id="separator_5"> |
154 | <property name="visible">True</property> |
155 | <property name="can_focus">False</property> |
156 | </object> |
157 | @@ -1024,7 +1041,6 @@ |
158 | <child> |
159 | <object class="GtkImageMenuItem" id="tcm_start_menu"> |
160 | <property name="label" translatable="yes">_Set start date</property> |
161 | - <property name="submenu">start_for_context_menu</property> |
162 | <property name="visible">True</property> |
163 | <property name="can_focus">False</property> |
164 | <property name="use_action_appearance">False</property> |
165 | @@ -1113,7 +1129,6 @@ |
166 | <child> |
167 | <object class="GtkImageMenuItem" id="tcm_due_menu"> |
168 | <property name="label" translatable="yes">Set due date</property> |
169 | - <property name="submenu">due_context_menu</property> |
170 | <property name="visible">True</property> |
171 | <property name="can_focus">False</property> |
172 | <property name="use_action_appearance">False</property> |
173 | |
174 | === modified file 'GTG/gtk/manager.py' |
175 | --- GTG/gtk/manager.py 2012-05-03 22:05:05 +0000 |
176 | +++ GTG/gtk/manager.py 2012-06-07 15:29:21 +0000 |
177 | @@ -34,6 +34,7 @@ |
178 | from GTG.gtk.browser.browser import TaskBrowser |
179 | from GTG.gtk.editor.editor import TaskEditor |
180 | from GTG.gtk.preferences import PreferencesDialog |
181 | +from GTG.gtk.plugins import PluginsDialog |
182 | from GTG.gtk.dbuswrapper import DBusTaskWrapper |
183 | from GTG.tools import clipboard |
184 | from GTG.core.plugins.engine import PluginEngine |
185 | @@ -83,7 +84,8 @@ |
186 | |
187 | #Preferences and Backends windows |
188 | # Initialize dialogs |
189 | - self.preferences_dialog = None |
190 | + self.preferences = PreferencesDialog(self.req) |
191 | + self.plugins = PluginsDialog(self.config_obj) |
192 | self.edit_backends_dialog = None |
193 | |
194 | # Tag Editor |
195 | @@ -224,10 +226,11 @@ |
196 | def configure_backend(self, backend_id): |
197 | self.open_edit_backends(None, backend_id) |
198 | |
199 | - def open_preferences(self, config_priv, sender=None): |
200 | - if not hasattr(self, "preferences"): |
201 | - self.preferences = PreferencesDialog(self.config_obj, self.req) |
202 | - self.preferences.activate(config_priv) |
203 | + def open_preferences(self, config_priv): |
204 | + self.preferences.activate() |
205 | + |
206 | + def configure_plugins(self): |
207 | + self.plugins.activate() |
208 | |
209 | def ask_delete_tasks(self, tids): |
210 | if not self.delete_dialog: |
211 | |
212 | === added file 'GTG/gtk/plugins.glade' |
213 | --- GTG/gtk/plugins.glade 1970-01-01 00:00:00 +0000 |
214 | +++ GTG/gtk/plugins.glade 2012-06-07 15:29:21 +0000 |
215 | @@ -0,0 +1,227 @@ |
216 | +<?xml version="1.0" encoding="UTF-8"?> |
217 | +<interface> |
218 | + <requires lib="gtk+" version="2.16"/> |
219 | + <!-- interface-naming-policy toplevel-contextual --> |
220 | + <object class="GtkAboutDialog" id="PluginAboutDialog"> |
221 | + <property name="can_focus">False</property> |
222 | + <property name="border_width">5</property> |
223 | + <property name="window_position">mouse</property> |
224 | + <property name="type_hint">dialog</property> |
225 | + <signal name="close" handler="on_PluginAboutDialog_close" swapped="no"/> |
226 | + <signal name="delete-event" handler="on_PluginAboutDialog_close" swapped="no"/> |
227 | + <signal name="response" handler="on_PluginAboutDialog_close" swapped="no"/> |
228 | + <child internal-child="vbox"> |
229 | + <object class="GtkVBox" id="pa-vbox1"> |
230 | + <property name="visible">True</property> |
231 | + <property name="can_focus">False</property> |
232 | + <property name="spacing">2</property> |
233 | + <child internal-child="action_area"> |
234 | + <object class="GtkHButtonBox" id="pa-action_area1"> |
235 | + <property name="visible">True</property> |
236 | + <property name="can_focus">False</property> |
237 | + <property name="layout_style">end</property> |
238 | + </object> |
239 | + <packing> |
240 | + <property name="expand">False</property> |
241 | + <property name="fill">True</property> |
242 | + <property name="pack_type">end</property> |
243 | + <property name="position">0</property> |
244 | + </packing> |
245 | + </child> |
246 | + <child> |
247 | + <object class="GtkFrame" id="pa-frame1"> |
248 | + <property name="visible">True</property> |
249 | + <property name="can_focus">False</property> |
250 | + <property name="label_xalign">0</property> |
251 | + <property name="shadow_type">none</property> |
252 | + <child> |
253 | + <object class="GtkAlignment" id="pa-alignment1"> |
254 | + <property name="visible">True</property> |
255 | + <property name="can_focus">False</property> |
256 | + <property name="left_padding">12</property> |
257 | + <child> |
258 | + <object class="GtkLabel" id="PluginDepends"> |
259 | + <property name="visible">True</property> |
260 | + <property name="can_focus">False</property> |
261 | + <property name="use_markup">True</property> |
262 | + </object> |
263 | + </child> |
264 | + </object> |
265 | + </child> |
266 | + <child type="label"> |
267 | + <object class="GtkLabel" id="pa-label1"> |
268 | + <property name="visible">True</property> |
269 | + <property name="can_focus">False</property> |
270 | + <property name="label" translatable="yes"><b>Dependencies</b></property> |
271 | + <property name="use_markup">True</property> |
272 | + </object> |
273 | + </child> |
274 | + </object> |
275 | + <packing> |
276 | + <property name="expand">True</property> |
277 | + <property name="fill">True</property> |
278 | + <property name="position">3</property> |
279 | + </packing> |
280 | + </child> |
281 | + </object> |
282 | + </child> |
283 | + </object> |
284 | + <object class="GtkDialog" id="PluginsDialog"> |
285 | + <property name="can_focus">False</property> |
286 | + <property name="border_width">10</property> |
287 | + <property name="window_position">center-on-parent</property> |
288 | + <property name="default_width">500</property> |
289 | + <property name="default_height">500</property> |
290 | + <property name="type_hint">dialog</property> |
291 | + <signal name="delete-event" handler="on_PluginsDialog_delete_event" swapped="no"/> |
292 | + <child internal-child="vbox"> |
293 | + <object class="GtkVBox" id="dialog-vbox5"> |
294 | + <property name="visible">True</property> |
295 | + <property name="can_focus">False</property> |
296 | + <child internal-child="action_area"> |
297 | + <object class="GtkHButtonBox" id="dialog-action_area5"> |
298 | + <property name="visible">True</property> |
299 | + <property name="can_focus">False</property> |
300 | + <property name="layout_style">end</property> |
301 | + <child> |
302 | + <object class="GtkButton" id="plugins_help"> |
303 | + <property name="label">gtk-help</property> |
304 | + <property name="can_focus">True</property> |
305 | + <property name="receives_default">True</property> |
306 | + <property name="no_show_all">True</property> |
307 | + <property name="use_action_appearance">False</property> |
308 | + <property name="use_stock">True</property> |
309 | + <signal name="released" handler="on_plugins_help" swapped="no"/> |
310 | + </object> |
311 | + <packing> |
312 | + <property name="expand">False</property> |
313 | + <property name="fill">False</property> |
314 | + <property name="position">0</property> |
315 | + </packing> |
316 | + </child> |
317 | + <child> |
318 | + <object class="GtkButton" id="plugins_close"> |
319 | + <property name="label">gtk-close</property> |
320 | + <property name="visible">True</property> |
321 | + <property name="can_focus">True</property> |
322 | + <property name="receives_default">True</property> |
323 | + <property name="use_action_appearance">False</property> |
324 | + <property name="use_stock">True</property> |
325 | + <signal name="released" handler="on_plugins_close" swapped="no"/> |
326 | + </object> |
327 | + <packing> |
328 | + <property name="expand">False</property> |
329 | + <property name="fill">False</property> |
330 | + <property name="position">1</property> |
331 | + </packing> |
332 | + </child> |
333 | + </object> |
334 | + <packing> |
335 | + <property name="expand">False</property> |
336 | + <property name="fill">True</property> |
337 | + <property name="pack_type">end</property> |
338 | + <property name="position">0</property> |
339 | + </packing> |
340 | + </child> |
341 | + <child> |
342 | + <object class="GtkVBox" id="plugins-vbox6"> |
343 | + <property name="visible">True</property> |
344 | + <property name="can_focus">False</property> |
345 | + <property name="spacing">6</property> |
346 | + <child> |
347 | + <object class="GtkScrolledWindow" id="plugins-scrolledwindow2"> |
348 | + <property name="width_request">240</property> |
349 | + <property name="visible">True</property> |
350 | + <property name="can_focus">True</property> |
351 | + <property name="hscrollbar_policy">automatic</property> |
352 | + <property name="vscrollbar_policy">automatic</property> |
353 | + <property name="shadow_type">in</property> |
354 | + <child> |
355 | + <object class="GtkTreeView" id="PluginTree"> |
356 | + <property name="visible">True</property> |
357 | + <property name="can_focus">True</property> |
358 | + <property name="headers_visible">False</property> |
359 | + <property name="rules_hint">True</property> |
360 | + <property name="show_expanders">False</property> |
361 | + <signal name="cursor-changed" handler="on_PluginTree_cursor_changed" swapped="no"/> |
362 | + </object> |
363 | + </child> |
364 | + </object> |
365 | + <packing> |
366 | + <property name="expand">True</property> |
367 | + <property name="fill">True</property> |
368 | + <property name="position">0</property> |
369 | + </packing> |
370 | + </child> |
371 | + <child> |
372 | + <object class="GtkHButtonBox" id="plugins-hbuttonbox1"> |
373 | + <property name="visible">True</property> |
374 | + <property name="can_focus">False</property> |
375 | + <property name="spacing">8</property> |
376 | + <property name="layout_style">end</property> |
377 | + <child> |
378 | + <object class="GtkButton" id="plugin_about"> |
379 | + <property name="label" translatable="yes">_About Plugin</property> |
380 | + <property name="visible">True</property> |
381 | + <property name="can_focus">True</property> |
382 | + <property name="receives_default">True</property> |
383 | + <property name="use_action_appearance">False</property> |
384 | + <property name="image">img_plugin_about</property> |
385 | + <property name="use_underline">True</property> |
386 | + <signal name="released" handler="on_plugin_about" swapped="no"/> |
387 | + </object> |
388 | + <packing> |
389 | + <property name="expand">False</property> |
390 | + <property name="fill">False</property> |
391 | + <property name="position">0</property> |
392 | + </packing> |
393 | + </child> |
394 | + <child> |
395 | + <object class="GtkButton" id="plugin_configure"> |
396 | + <property name="label">C_onfigure Plugin</property> |
397 | + <property name="sensitive">False</property> |
398 | + <property name="can_focus">True</property> |
399 | + <property name="receives_default">True</property> |
400 | + <property name="use_action_appearance">False</property> |
401 | + <property name="image">img_plugin_conf</property> |
402 | + <property name="use_underline">True</property> |
403 | + <signal name="released" handler="on_plugin_configure" swapped="no"/> |
404 | + </object> |
405 | + <packing> |
406 | + <property name="expand">False</property> |
407 | + <property name="fill">False</property> |
408 | + <property name="position">1</property> |
409 | + </packing> |
410 | + </child> |
411 | + </object> |
412 | + <packing> |
413 | + <property name="expand">False</property> |
414 | + <property name="fill">True</property> |
415 | + <property name="position">1</property> |
416 | + </packing> |
417 | + </child> |
418 | + </object> |
419 | + <packing> |
420 | + <property name="expand">True</property> |
421 | + <property name="fill">True</property> |
422 | + <property name="position">3</property> |
423 | + </packing> |
424 | + </child> |
425 | + </object> |
426 | + </child> |
427 | + <action-widgets> |
428 | + <action-widget response="0">plugins_help</action-widget> |
429 | + <action-widget response="0">plugins_close</action-widget> |
430 | + </action-widgets> |
431 | + </object> |
432 | + <object class="GtkImage" id="img_plugin_about"> |
433 | + <property name="visible">True</property> |
434 | + <property name="can_focus">False</property> |
435 | + <property name="stock">gtk-about</property> |
436 | + </object> |
437 | + <object class="GtkImage" id="img_plugin_conf"> |
438 | + <property name="visible">True</property> |
439 | + <property name="can_focus">False</property> |
440 | + <property name="stock">gtk-preferences</property> |
441 | + </object> |
442 | +</interface> |
443 | |
444 | === added file 'GTG/gtk/plugins.py' |
445 | --- GTG/gtk/plugins.py 1970-01-01 00:00:00 +0000 |
446 | +++ GTG/gtk/plugins.py 2012-06-07 15:29:21 +0000 |
447 | @@ -0,0 +1,322 @@ |
448 | +# -*- coding: utf-8 -*- |
449 | +# ----------------------------------------------------------------------------- |
450 | +# Gettings Things Gnome! - a personal organizer for the GNOME desktop |
451 | +# Copyright (c) 2008-2012 - Lionel Dricot & Bertrand Rousseau |
452 | +# |
453 | +# This program is free software: you can redistribute it and/or modify it under |
454 | +# the terms of the GNU General Public License as published by the Free Software |
455 | +# Foundation, either version 3 of the License, or (at your option) any later |
456 | +# version. |
457 | +# |
458 | +# This program is distributed in the hope that it will be useful, but WITHOUT |
459 | +# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS |
460 | +# FOR A PARTICULAR PURPOSE. See the GNU General Public License for more |
461 | +# details. |
462 | +# |
463 | +# You should have received a copy of the GNU General Public License along with |
464 | +# this program. If not, see <http://www.gnu.org/licenses/>. |
465 | +# ----------------------------------------------------------------------------- |
466 | + |
467 | +""" Dialog for configuring plugins """ |
468 | + |
469 | +import gtk |
470 | +import pango |
471 | + |
472 | +from GTG import _ |
473 | +from GTG import info |
474 | +from GTG.core.plugins import GnomeConfig |
475 | +from GTG.core.plugins.engine import PluginEngine |
476 | +from GTG.gtk import ViewConfig |
477 | + |
478 | +# columns in PluginsDialog.plugin_store |
479 | +PLUGINS_COL_ID = 0 |
480 | +PLUGINS_COL_ENABLED = 1 |
481 | +PLUGINS_COL_NAME = 2 |
482 | +PLUGINS_COL_SHORT_DESC = 3 |
483 | +PLUGINS_COL_ACTIVATABLE = 4 |
484 | + |
485 | + |
486 | +def plugin_icon(column, cell, store, iterator): # pylint: disable-msg=W0613 |
487 | + """ Callback to set the content of a PluginTree cell. |
488 | + |
489 | + See PluginsDialog._init_plugin_tree(). |
490 | + """ |
491 | + cell.set_property('icon-name', 'gtg-plugin') |
492 | + cell.set_property('sensitive', |
493 | + store.get_value(iterator, PLUGINS_COL_ACTIVATABLE)) |
494 | + |
495 | + |
496 | +def plugin_error_short_text(plugin): |
497 | + """ Return small version of description of missing module dependencies |
498 | + for displaying in plugin markup """ |
499 | + if not plugin.error: |
500 | + return "" |
501 | + |
502 | + # get lists |
503 | + modules = plugin.missing_modules |
504 | + dbus = plugin.missing_dbus |
505 | + |
506 | + # convert to strings |
507 | + if modules: |
508 | + modules = "<small><b>%s</b></small>" % ', '.join(modules) |
509 | + if dbus: |
510 | + ifaces = ["%s:%s" % (a, b) for (a, b) in dbus] |
511 | + dbus = "<small><b>%s</b></small>" % ', '.join(ifaces) |
512 | + |
513 | + # combine |
514 | + if modules and not dbus: |
515 | + text = '\n'.join((GnomeConfig.miss2, modules)) |
516 | + elif dbus and not modules: |
517 | + text = '\n'.join((GnomeConfig.dmiss2, dbus)) |
518 | + elif modules and dbus: |
519 | + text = '\n'.join((GnomeConfig.bmiss2, modules, dbus)) |
520 | + else: |
521 | + text = "" |
522 | + |
523 | + return text |
524 | + |
525 | + |
526 | +def plugin_error_text(plugin): |
527 | + """ Generate some helpful text about missing module dependencies. """ |
528 | + if not plugin.error: |
529 | + return GnomeConfig.CANLOAD |
530 | + |
531 | + # describe missing dependencies |
532 | + text = "<b>%s</b>. \n" % GnomeConfig.CANNOTLOAD |
533 | + # get lists |
534 | + modules = plugin.missing_modules |
535 | + dbus = plugin.missing_dbus |
536 | + |
537 | + # convert to strings |
538 | + if modules: |
539 | + modules = "<small><b>%s</b></small>" % ', '.join(modules) |
540 | + if dbus: |
541 | + ifaces = ["%s:%s" % (a, b) for (a, b) in dbus] |
542 | + dbus = "<small><b>%s</b></small>" % ', '.join(ifaces) |
543 | + |
544 | + # combine |
545 | + if modules and not dbus: |
546 | + text += '\n'.join((GnomeConfig.MODULEMISSING, modules)) |
547 | + elif dbus and not modules: |
548 | + text += '\n'.join((GnomeConfig.DBUSMISSING, dbus)) |
549 | + elif modules and dbus: |
550 | + text += '\n'.join((GnomeConfig.MODULANDDBUS, modules, dbus)) |
551 | + else: |
552 | + text += GnomeConfig.UNKNOWN |
553 | + |
554 | + return text |
555 | + |
556 | + |
557 | +def plugin_markup(column, cell, store, iterator, self): |
558 | + # pylint: disable-msg=W0613 |
559 | + """ Callback to set the content of a PluginTree cell. |
560 | + |
561 | + See PluginsDialog._init_plugin_tree(). |
562 | + """ |
563 | + name = store.get_value(iterator, PLUGINS_COL_NAME) |
564 | + desc = store.get_value(iterator, PLUGINS_COL_SHORT_DESC) |
565 | + |
566 | + plugin_id = store.get_value(iterator, PLUGINS_COL_ID) |
567 | + plugin = self.pengine.get_plugin(plugin_id) |
568 | + error_text = plugin_error_short_text(plugin) |
569 | + if error_text != "": |
570 | + text = "<b>%s</b>\n%s\n<i>%s</i>" % (name, desc, error_text) |
571 | + else: |
572 | + text = "<b>%s</b>\n%s" % (name, desc) |
573 | + |
574 | + cell.set_property('markup', text) |
575 | + cell.set_property('sensitive', |
576 | + store.get_value(iterator, PLUGINS_COL_ACTIVATABLE)) |
577 | + |
578 | + |
579 | +class PluginsDialog: |
580 | + """ Dialog for Plugins configuration """ |
581 | + # pylint: disable-msg=R0902 |
582 | + def __init__(self, config_obj): |
583 | + self.config_obj = config_obj |
584 | + self.config = self.config_obj.conf_dict |
585 | + builder = gtk.Builder() |
586 | + builder.add_from_file(ViewConfig.PLUGINS_GLADE_FILE) |
587 | + |
588 | + self.dialog = builder.get_object("PluginsDialog") |
589 | + self.dialog.set_title(_("Plugins - %s" % info.NAME)) |
590 | + self.plugin_tree = builder.get_object("PluginTree") |
591 | + self.plugin_configure = builder.get_object("plugin_configure") |
592 | + self.plugin_about = builder.get_object("PluginAboutDialog") |
593 | + self.plugin_depends = builder.get_object('PluginDepends') |
594 | + |
595 | + self.pengine = PluginEngine() |
596 | + #plugin config initiation, if never used |
597 | + if "plugins" in self.config: |
598 | + if "enabled" not in self.config["plugins"]: |
599 | + self.config["plugins"]["enabled"] = [] |
600 | + |
601 | + if "disabled" not in self.config["plugins"]: |
602 | + self.config["plugins"]["disabled"] = [] |
603 | + elif self.pengine.get_plugins(): |
604 | + self.config["plugins"] = {} |
605 | + self.config["plugins"]["disabled"] = \ |
606 | + [p.module_name for p in self.pengine.get_plugins("disabled")] |
607 | + self.config["plugins"]["enabled"] = \ |
608 | + [p.module_name for p in self.pengine.get_plugins("enabled")] |
609 | + |
610 | + # see constants PLUGINS_COL_* for column meanings |
611 | + self.plugin_store = gtk.ListStore(str, bool, str, str, bool) |
612 | + |
613 | + builder.connect_signals({ |
614 | + 'on_plugins_help': |
615 | + self.on_help, |
616 | + 'on_plugins_close': |
617 | + self.on_close, |
618 | + 'on_PluginsDialog_delete_event': |
619 | + self.on_close, |
620 | + 'on_PluginTree_cursor_changed': |
621 | + self.on_plugin_select, |
622 | + 'on_plugin_about': |
623 | + self.on_plugin_about, |
624 | + 'on_plugin_configure': |
625 | + self.on_plugin_configure, |
626 | + 'on_PluginAboutDialog_close': |
627 | + self.on_plugin_about_close, |
628 | + }) |
629 | + |
630 | + def _init_plugin_tree(self): |
631 | + """ Initialize the PluginTree gtk.TreeView. |
632 | + |
633 | + The format is modelled after the one used in gedit; see |
634 | + http://git.gnome.org/browse/gedit/tree/gedit/gedit-plugin-mapnager.c |
635 | + """ |
636 | + # force creation of the gtk.ListStore so we can reference it |
637 | + self._refresh_plugin_store() |
638 | + |
639 | + # renderer for the toggle column |
640 | + renderer = gtk.CellRendererToggle() |
641 | + renderer.set_property('xpad', 6) |
642 | + renderer.connect('toggled', self.on_plugin_toggle) |
643 | + # toggle column |
644 | + column = gtk.TreeViewColumn(None, renderer, active=PLUGINS_COL_ENABLED, |
645 | + activatable=PLUGINS_COL_ACTIVATABLE, |
646 | + sensitive=PLUGINS_COL_ACTIVATABLE) |
647 | + self.plugin_tree.append_column(column) |
648 | + |
649 | + # plugin name column |
650 | + column = gtk.TreeViewColumn() |
651 | + column.set_spacing(6) |
652 | + # icon renderer for the plugin name column |
653 | + icon_renderer = gtk.CellRendererPixbuf() |
654 | + icon_renderer.set_property('stock-size', gtk.ICON_SIZE_SMALL_TOOLBAR) |
655 | + icon_renderer.set_property('xpad', 3) |
656 | + column.pack_start(icon_renderer, expand=False) |
657 | + column.set_cell_data_func(icon_renderer, plugin_icon) |
658 | + # text renderer for the plugin name column |
659 | + name_renderer = gtk.CellRendererText() |
660 | + name_renderer.set_property('ellipsize', pango.ELLIPSIZE_END) |
661 | + column.pack_start(name_renderer) |
662 | + column.set_cell_data_func(name_renderer, plugin_markup, self) |
663 | + |
664 | + self.plugin_tree.append_column(column) |
665 | + |
666 | + # finish setup |
667 | + self.plugin_tree.set_model(self.plugin_store) |
668 | + self.plugin_tree.set_search_column(2) |
669 | + |
670 | + def _refresh_plugin_store(self): |
671 | + """ Refresh status of plugins and put it in a gtk.ListStore """ |
672 | + self.plugin_store.clear() |
673 | + self.pengine.recheck_plugin_errors(True) |
674 | + for name, plugin in self.pengine.plugins.iteritems(): |
675 | + # activateable if there is no error |
676 | + self.plugin_store.append((name, plugin.enabled, plugin.full_name, |
677 | + plugin.short_description, not plugin.error)) |
678 | + |
679 | + def activate(self): |
680 | + """ Refresh status of plugins and show the dialog """ |
681 | + if len(self.plugin_tree.get_columns()) == 0: |
682 | + self._init_plugin_tree() |
683 | + else: |
684 | + self._refresh_plugin_store() |
685 | + self.dialog.show_all() |
686 | + |
687 | + def on_close(self, widget, data=None): # pylint: disable-msg=W0613 |
688 | + """ Close the plugins dialog.""" |
689 | + self.dialog.hide() |
690 | + return True |
691 | + |
692 | + @classmethod |
693 | + def on_help(cls, widget): # pylint: disable-msg=W0613 |
694 | + """ In future, this will open help for plugins """ |
695 | + return True |
696 | + |
697 | + def on_plugin_toggle(self, widget, path): # pylint: disable-msg=W0613 |
698 | + """Toggle a plugin enabled/disabled.""" |
699 | + iterator = self.plugin_store.get_iter(path) |
700 | + plugin_id = self.plugin_store.get_value(iterator, PLUGINS_COL_ID) |
701 | + plugin = self.pengine.get_plugin(plugin_id) |
702 | + plugin.enabled = not self.plugin_store.get_value(iterator, |
703 | + PLUGINS_COL_ENABLED) |
704 | + if plugin.enabled: |
705 | + self.pengine.activate_plugins([plugin]) |
706 | + self.config["plugins"]["enabled"].append(plugin.module_name) |
707 | + if plugin.module_name in self.config["plugins"]["disabled"]: |
708 | + self.config["plugins"]["disabled"].remove(plugin.module_name) |
709 | + else: |
710 | + self.pengine.deactivate_plugins([plugin]) |
711 | + self.config["plugins"]["disabled"].append(plugin.module_name) |
712 | + if plugin.module_name in self.config["plugins"]["enabled"]: |
713 | + self.config["plugins"]["enabled"].remove(plugin.module_name) |
714 | + self.plugin_store.set_value(iterator, PLUGINS_COL_ENABLED, |
715 | + plugin.enabled) |
716 | + self._update_plugin_configure(plugin) |
717 | + |
718 | + self.config_obj.save() |
719 | + |
720 | + def on_plugin_select(self, plugin_tree): |
721 | + """ Callback when user select/unselect a plugin |
722 | + |
723 | + Update the button "Configure plugin" sensitivity """ |
724 | + model, iterator = plugin_tree.get_selection().get_selected() |
725 | + if iterator is not None: |
726 | + plugin_id = model.get_value(iterator, PLUGINS_COL_ID) |
727 | + plugin = self.pengine.get_plugin(plugin_id) |
728 | + self._update_plugin_configure(plugin) |
729 | + |
730 | + def _update_plugin_configure(self, plugin): |
731 | + """ Enable the button "Configure Plugin" appropriate. """ |
732 | + configurable = plugin.active and plugin.is_configurable() |
733 | + self.plugin_configure.set_property('sensitive', configurable) |
734 | + |
735 | + def on_plugin_configure(self, widget): # pylint: disable-msg=W0613 |
736 | + """ Show the dialog for plugin configuration """ |
737 | + _, iterator = self.plugin_tree.get_selection().get_selected() |
738 | + if iterator is None: |
739 | + return |
740 | + plugin_id = self.plugin_store.get_value(iterator, PLUGINS_COL_ID) |
741 | + plugin = self.pengine.get_plugin(plugin_id) |
742 | + plugin.instance.configure_dialog(self.dialog) |
743 | + |
744 | + def on_plugin_about(self, widget): # pylint: disable-msg=W0613 |
745 | + """ Display information about a plugin. """ |
746 | + _, iterator = self.plugin_tree.get_selection().get_selected() |
747 | + if iterator is None: |
748 | + return |
749 | + plugin_id = self.plugin_store.get_value(iterator, PLUGINS_COL_ID) |
750 | + plugin = self.pengine.get_plugin(plugin_id) |
751 | + |
752 | + self.plugin_about.set_name(plugin.full_name) |
753 | + self.plugin_about.set_version(plugin.version) |
754 | + authors = plugin.authors |
755 | + if isinstance(authors, str): |
756 | + authors = "\n".join(author.strip() |
757 | + for author in authors.split(',')) |
758 | + authors = [authors, ] |
759 | + self.plugin_about.set_authors(authors) |
760 | + description = plugin.description.replace(r'\n', "\n") |
761 | + self.plugin_about.set_comments(description) |
762 | + self.plugin_depends.set_label(plugin_error_text(plugin)) |
763 | + self.plugin_about.show_all() |
764 | + |
765 | + def on_plugin_about_close(self, widget, data=None): |
766 | + # pylint: disable-msg=W0613 |
767 | + """ Close the PluginAboutDialog. """ |
768 | + self.plugin_about.hide() |
769 | + return True |
770 | |
771 | === modified file 'GTG/gtk/preferences.glade' |
772 | --- GTG/gtk/preferences.glade 2012-05-24 11:48:45 +0000 |
773 | +++ GTG/gtk/preferences.glade 2012-06-07 15:29:21 +0000 |
774 | @@ -1,376 +1,210 @@ |
775 | -<?xml version="1.0"?> |
776 | +<?xml version="1.0" encoding="UTF-8"?> |
777 | <interface> |
778 | <requires lib="gtk+" version="2.16"/> |
779 | <!-- interface-naming-policy toplevel-contextual --> |
780 | - <object class="GtkAccelGroup" id="accelgroup1"/> |
781 | - <object class="GtkImage" id="image1"> |
782 | - <property name="visible">True</property> |
783 | - <property name="stock">gtk-save-as</property> |
784 | - </object> |
785 | <object class="GtkDialog" id="PreferencesDialog"> |
786 | - <property name="border_width">5</property> |
787 | - <property name="title" translatable="yes">Preferences - Getting Things GNOME!</property> |
788 | + <property name="can_focus">False</property> |
789 | + <property name="border_width">3</property> |
790 | <property name="window_position">center-on-parent</property> |
791 | - <property name="default_width">500</property> |
792 | - <property name="default_height">500</property> |
793 | <property name="type_hint">dialog</property> |
794 | - <signal name="delete_event" handler="on_PreferencesDialog_delete_event"/> |
795 | + <signal name="delete-event" handler="on_PreferencesDialog_delete_event" swapped="no"/> |
796 | <child internal-child="vbox"> |
797 | <object class="GtkVBox" id="prefs-vbox1"> |
798 | <property name="visible">True</property> |
799 | + <property name="can_focus">False</property> |
800 | <child> |
801 | - <object class="GtkAlignment" id="prefs-alignment1"> |
802 | + <object class="GtkNotebook" id="notebook1"> |
803 | <property name="visible">True</property> |
804 | - <property name="top_padding">6</property> |
805 | - <property name="bottom_padding">6</property> |
806 | - <property name="left_padding">6</property> |
807 | - <property name="right_padding">6</property> |
808 | + <property name="can_focus">True</property> |
809 | + <property name="show_tabs">False</property> |
810 | <child> |
811 | - <object class="GtkNotebook" id="prefs-notebook1"> |
812 | + <object class="GtkVBox" id="prefs-vbox2"> |
813 | <property name="visible">True</property> |
814 | - <property name="can_focus">True</property> |
815 | + <property name="can_focus">False</property> |
816 | <child> |
817 | - <object class="GtkAlignment" id="prefs-alignment2"> |
818 | + <object class="GtkFrame" id="prefs-frame3"> |
819 | <property name="visible">True</property> |
820 | - <property name="top_padding">10</property> |
821 | - <property name="bottom_padding">10</property> |
822 | - <property name="left_padding">10</property> |
823 | - <property name="right_padding">10</property> |
824 | + <property name="can_focus">False</property> |
825 | + <property name="label_xalign">0</property> |
826 | + <property name="shadow_type">none</property> |
827 | <child> |
828 | - <object class="GtkVBox" id="prefs-vbox2"> |
829 | - <property name="visible">True</property> |
830 | - <child> |
831 | - <object class="GtkFrame" id="prefs-frame3"> |
832 | - <property name="visible">True</property> |
833 | - <property name="label_xalign">0</property> |
834 | - <property name="shadow_type">none</property> |
835 | - <child> |
836 | - <object class="GtkAlignment" id="prefs-alignment7"> |
837 | - <property name="visible">True</property> |
838 | - <property name="bottom_padding">15</property> |
839 | - <property name="left_padding">12</property> |
840 | - <child> |
841 | - <object class="GtkVBox" id="prefs-vbox7"> |
842 | - <property name="visible">True</property> |
843 | - <child> |
844 | - <object class="GtkCheckButton" id="pref_autostart"> |
845 | - <property name="label" translatable="yes">Start Getting Things GNOME! on every login</property> |
846 | - <property name="visible">True</property> |
847 | - <property name="can_focus">True</property> |
848 | - <property name="receives_default">False</property> |
849 | - <property name="draw_indicator">True</property> |
850 | - <signal name="toggled" handler="on_pref_autostart_toggled"/> |
851 | - </object> |
852 | - <packing> |
853 | - <property name="expand">False</property> |
854 | - <property name="padding">3</property> |
855 | - <property name="position">0</property> |
856 | - </packing> |
857 | - </child> |
858 | - </object> |
859 | - </child> |
860 | - </object> |
861 | - </child> |
862 | - <child type="label"> |
863 | - <object class="GtkLabel" id="prefs-label8"> |
864 | - <property name="visible">True</property> |
865 | - <property name="ypad">5</property> |
866 | - <property name="label" translatable="yes"><b>Startup</b></property> |
867 | - <property name="use_markup">True</property> |
868 | - </object> |
869 | - </child> |
870 | - </object> |
871 | - <packing> |
872 | - <property name="expand">False</property> |
873 | - <property name="position">0</property> |
874 | - </packing> |
875 | - </child> |
876 | - <child> |
877 | - <object class="GtkFrame" id="prefs-frame1"> |
878 | - <property name="visible">True</property> |
879 | - <property name="label_xalign">0</property> |
880 | - <property name="shadow_type">none</property> |
881 | - <child> |
882 | - <object class="GtkAlignment" id="prefs-alignment5"> |
883 | - <property name="visible">True</property> |
884 | - <property name="bottom_padding">15</property> |
885 | - <property name="left_padding">12</property> |
886 | - <child> |
887 | - <object class="GtkVBox" id="prefs-vbox3"> |
888 | - <property name="visible">True</property> |
889 | - <child> |
890 | - <object class="GtkCheckButton" id="pref_show_preview"> |
891 | - <property name="label" translatable="yes">Show description preview in the task list.</property> |
892 | - <property name="visible">True</property> |
893 | - <property name="can_focus">True</property> |
894 | - <property name="receives_default">False</property> |
895 | - <property name="draw_indicator">True</property> |
896 | - <signal name="toggled" handler="on_pref_show_preview_toggled"/> |
897 | - </object> |
898 | - <packing> |
899 | - <property name="expand">False</property> |
900 | - <property name="padding">3</property> |
901 | - <property name="position">0</property> |
902 | - </packing> |
903 | - </child> |
904 | - <child> |
905 | - <object class="GtkCheckButton" id="bg_color_enable"> |
906 | - <property name="label" translatable="yes">Enable colored backgrounds in the task list</property> |
907 | - <property name="visible">True</property> |
908 | - <property name="can_focus">True</property> |
909 | - <property name="receives_default">False</property> |
910 | - <property name="draw_indicator">True</property> |
911 | - <signal name="toggled" handler="on_bg_color_toggled"/> |
912 | - </object> |
913 | - <packing> |
914 | - <property name="expand">False</property> |
915 | - <property name="padding">3</property> |
916 | - <property name="position">1</property> |
917 | - </packing> |
918 | - </child> |
919 | - <child> |
920 | - <object class="GtkHBox" id="prefs-hbox1"> |
921 | - <property name="no_show_all">True</property> |
922 | - <child> |
923 | - <object class="GtkCheckButton" id="pref_hide_closed"> |
924 | - <property name="label" translatable="yes">Hide closed tasks older than </property> |
925 | - <property name="visible">True</property> |
926 | - <property name="sensitive">False</property> |
927 | - <property name="can_focus">True</property> |
928 | - <property name="receives_default">False</property> |
929 | - <property name="draw_indicator">True</property> |
930 | - </object> |
931 | - <packing> |
932 | - <property name="expand">False</property> |
933 | - <property name="position">0</property> |
934 | - </packing> |
935 | - </child> |
936 | - <child> |
937 | - <object class="GtkComboBox" id="pref_hide_closed_age"> |
938 | - <property name="visible">True</property> |
939 | - <property name="sensitive">False</property> |
940 | - <property name="can_focus">True</property> |
941 | - </object> |
942 | - <packing> |
943 | - <property name="position">1</property> |
944 | - </packing> |
945 | - </child> |
946 | - </object> |
947 | - <packing> |
948 | - <property name="expand">False</property> |
949 | - <property name="padding">3</property> |
950 | - <property name="position">2</property> |
951 | - </packing> |
952 | - </child> |
953 | - </object> |
954 | - </child> |
955 | - </object> |
956 | - </child> |
957 | - <child type="label"> |
958 | - <object class="GtkLabel" id="prefs-label4"> |
959 | - <property name="visible">True</property> |
960 | - <property name="ypad">5</property> |
961 | - <property name="label" translatable="yes"><b>Task Browser</b></property> |
962 | - <property name="use_markup">True</property> |
963 | - </object> |
964 | - </child> |
965 | - </object> |
966 | - <packing> |
967 | - <property name="expand">False</property> |
968 | - <property name="position">1</property> |
969 | - </packing> |
970 | - </child> |
971 | - <child> |
972 | - <object class="GtkFrame" id="prefs-frame2"> |
973 | - <property name="visible">True</property> |
974 | - <property name="label_xalign">0</property> |
975 | - <property name="shadow_type">none</property> |
976 | - <child> |
977 | - <object class="GtkAlignment" id="prefs-alignment6"> |
978 | - <property name="visible">True</property> |
979 | - <property name="bottom_padding">15</property> |
980 | - <property name="left_padding">12</property> |
981 | - <child> |
982 | - <object class="GtkVBox" id="prefs-vbox4"> |
983 | - <property name="visible">True</property> |
984 | - <child> |
985 | - <object class="GtkCheckButton" id="pref_check_spelling"> |
986 | - <property name="label" translatable="yes">Check spelling</property> |
987 | - <property name="sensitive">False</property> |
988 | - <property name="can_focus">True</property> |
989 | - <property name="receives_default">False</property> |
990 | - <property name="no_show_all">True</property> |
991 | - <property name="draw_indicator">True</property> |
992 | - <signal name="toggled" handler="on_pref_check_spelling_toggled"/> |
993 | - </object> |
994 | - <packing> |
995 | - <property name="expand">False</property> |
996 | - <property name="padding">3</property> |
997 | - <property name="position">0</property> |
998 | - </packing> |
999 | - </child> |
1000 | - </object> |
1001 | - </child> |
1002 | - </object> |
1003 | - </child> |
1004 | - <child type="label"> |
1005 | - <object class="GtkLabel" id="prefs-label5"> |
1006 | - <property name="no_show_all">True</property> |
1007 | - <property name="ypad">5</property> |
1008 | - <property name="label" translatable="yes"><b>Task Editor</b></property> |
1009 | - <property name="use_markup">True</property> |
1010 | - </object> |
1011 | - </child> |
1012 | - </object> |
1013 | - <packing> |
1014 | - <property name="expand">False</property> |
1015 | - <property name="position">2</property> |
1016 | - </packing> |
1017 | - </child> |
1018 | - </object> |
1019 | - </child> |
1020 | - </object> |
1021 | - </child> |
1022 | - <child type="tab"> |
1023 | - <object class="GtkLabel" id="prefs-label1"> |
1024 | - <property name="visible">True</property> |
1025 | - <property name="label" translatable="yes">General</property> |
1026 | + <object class="GtkAlignment" id="prefs-alignment7"> |
1027 | + <property name="visible">True</property> |
1028 | + <property name="can_focus">False</property> |
1029 | + <property name="bottom_padding">15</property> |
1030 | + <property name="left_padding">12</property> |
1031 | + <child> |
1032 | + <object class="GtkVBox" id="prefs-vbox7"> |
1033 | + <property name="visible">True</property> |
1034 | + <property name="can_focus">False</property> |
1035 | + <child> |
1036 | + <object class="GtkCheckButton" id="pref_autostart"> |
1037 | + <property name="label" translatable="yes">Start Getting Things GNOME! on every login</property> |
1038 | + <property name="visible">True</property> |
1039 | + <property name="can_focus">True</property> |
1040 | + <property name="receives_default">False</property> |
1041 | + <property name="use_action_appearance">False</property> |
1042 | + <property name="draw_indicator">True</property> |
1043 | + <signal name="toggled" handler="on_pref_autostart_toggled" swapped="no"/> |
1044 | + </object> |
1045 | + <packing> |
1046 | + <property name="expand">False</property> |
1047 | + <property name="fill">True</property> |
1048 | + <property name="padding">3</property> |
1049 | + <property name="position">0</property> |
1050 | + </packing> |
1051 | + </child> |
1052 | + </object> |
1053 | + </child> |
1054 | + </object> |
1055 | + </child> |
1056 | + <child type="label"> |
1057 | + <object class="GtkLabel" id="prefs-label8"> |
1058 | + <property name="visible">True</property> |
1059 | + <property name="can_focus">False</property> |
1060 | + <property name="ypad">5</property> |
1061 | + <property name="label" translatable="yes"><b>Startup</b></property> |
1062 | + <property name="use_markup">True</property> |
1063 | + </object> |
1064 | + </child> |
1065 | </object> |
1066 | <packing> |
1067 | - <property name="tab_fill">False</property> |
1068 | + <property name="expand">False</property> |
1069 | + <property name="fill">True</property> |
1070 | + <property name="position">1</property> |
1071 | </packing> |
1072 | </child> |
1073 | <child> |
1074 | - <placeholder/> |
1075 | - </child> |
1076 | - <child type="tab"> |
1077 | - <placeholder/> |
1078 | - </child> |
1079 | - <child> |
1080 | - <object class="GtkAlignment" id="prefs-alignment4"> |
1081 | + <object class="GtkFrame" id="prefs-frame1"> |
1082 | <property name="visible">True</property> |
1083 | - <property name="top_padding">10</property> |
1084 | - <property name="bottom_padding">10</property> |
1085 | - <property name="left_padding">10</property> |
1086 | - <property name="right_padding">10</property> |
1087 | + <property name="can_focus">False</property> |
1088 | + <property name="label_xalign">0</property> |
1089 | + <property name="shadow_type">none</property> |
1090 | <child> |
1091 | - <object class="GtkVBox" id="prefs-vbox6"> |
1092 | + <object class="GtkAlignment" id="prefs-alignment5"> |
1093 | <property name="visible">True</property> |
1094 | - <property name="spacing">6</property> |
1095 | - <child> |
1096 | - <object class="GtkLabel" id="prefs-label7"> |
1097 | - <property name="visible">True</property> |
1098 | - <property name="xalign">0</property> |
1099 | - <property name="label" translatable="yes">Active _Plugins:</property> |
1100 | - <property name="use_underline">True</property> |
1101 | - </object> |
1102 | - <packing> |
1103 | - <property name="expand">False</property> |
1104 | - <property name="position">0</property> |
1105 | - </packing> |
1106 | - </child> |
1107 | - <child> |
1108 | - <object class="GtkScrolledWindow" id="prefs-scrolledwindow2"> |
1109 | - <property name="width_request">240</property> |
1110 | - <property name="visible">True</property> |
1111 | - <property name="can_focus">True</property> |
1112 | - <property name="hscrollbar_policy">automatic</property> |
1113 | - <property name="vscrollbar_policy">automatic</property> |
1114 | - <property name="shadow_type">in</property> |
1115 | - <child> |
1116 | - <object class="GtkTreeView" id="PluginTree"> |
1117 | - <property name="visible">True</property> |
1118 | - <property name="can_focus">True</property> |
1119 | - <property name="headers_visible">False</property> |
1120 | - <property name="rules_hint">True</property> |
1121 | - <property name="show_expanders">False</property> |
1122 | - <signal name="cursor_changed" handler="on_PluginTree_cursor_changed"/> |
1123 | - </object> |
1124 | - </child> |
1125 | - </object> |
1126 | - <packing> |
1127 | - <property name="position">1</property> |
1128 | - </packing> |
1129 | - </child> |
1130 | - <child> |
1131 | - <object class="GtkHButtonBox" id="prefs-hbuttonbox1"> |
1132 | - <property name="visible">True</property> |
1133 | - <property name="spacing">8</property> |
1134 | - <property name="layout_style">end</property> |
1135 | - <child> |
1136 | - <object class="GtkButton" id="plugin_about"> |
1137 | - <property name="label" translatable="yes">_About Plugin</property> |
1138 | - <property name="visible">True</property> |
1139 | - <property name="can_focus">True</property> |
1140 | - <property name="receives_default">True</property> |
1141 | - <property name="image">pref_img_plugin_about</property> |
1142 | - <property name="use_underline">True</property> |
1143 | - <signal name="released" handler="on_plugin_about"/> |
1144 | + <property name="can_focus">False</property> |
1145 | + <property name="bottom_padding">15</property> |
1146 | + <property name="left_padding">12</property> |
1147 | + <child> |
1148 | + <object class="GtkVBox" id="prefs-vbox3"> |
1149 | + <property name="visible">True</property> |
1150 | + <property name="can_focus">False</property> |
1151 | + <child> |
1152 | + <object class="GtkCheckButton" id="pref_show_preview"> |
1153 | + <property name="label" translatable="yes">Show description preview in the task list.</property> |
1154 | + <property name="visible">True</property> |
1155 | + <property name="can_focus">True</property> |
1156 | + <property name="receives_default">False</property> |
1157 | + <property name="use_action_appearance">False</property> |
1158 | + <property name="draw_indicator">True</property> |
1159 | + <signal name="toggled" handler="on_pref_show_preview_toggled" swapped="no"/> |
1160 | </object> |
1161 | <packing> |
1162 | <property name="expand">False</property> |
1163 | - <property name="fill">False</property> |
1164 | + <property name="fill">True</property> |
1165 | + <property name="padding">3</property> |
1166 | <property name="position">0</property> |
1167 | </packing> |
1168 | </child> |
1169 | <child> |
1170 | - <object class="GtkButton" id="plugin_configure"> |
1171 | - <property name="label">C_onfigure Plugin</property> |
1172 | - <property name="sensitive">False</property> |
1173 | + <object class="GtkCheckButton" id="bg_color_enable"> |
1174 | + <property name="label" translatable="yes">Enable colored backgrounds in the task list</property> |
1175 | + <property name="visible">True</property> |
1176 | <property name="can_focus">True</property> |
1177 | - <property name="receives_default">True</property> |
1178 | - <property name="image">pref_img_plugin_conf</property> |
1179 | - <property name="use_underline">True</property> |
1180 | - <signal name="released" handler="on_plugin_configure"/> |
1181 | + <property name="receives_default">False</property> |
1182 | + <property name="use_action_appearance">False</property> |
1183 | + <property name="draw_indicator">True</property> |
1184 | + <signal name="toggled" handler="on_bg_color_toggled" swapped="no"/> |
1185 | </object> |
1186 | <packing> |
1187 | <property name="expand">False</property> |
1188 | - <property name="fill">False</property> |
1189 | + <property name="fill">True</property> |
1190 | + <property name="padding">3</property> |
1191 | <property name="position">1</property> |
1192 | </packing> |
1193 | </child> |
1194 | </object> |
1195 | - <packing> |
1196 | - <property name="expand">False</property> |
1197 | - <property name="position">2</property> |
1198 | - </packing> |
1199 | </child> |
1200 | </object> |
1201 | </child> |
1202 | - </object> |
1203 | - <packing> |
1204 | - <property name="position">2</property> |
1205 | - </packing> |
1206 | - </child> |
1207 | - <child type="tab"> |
1208 | - <object class="GtkLabel" id="prefs-label3"> |
1209 | - <property name="visible">True</property> |
1210 | - <property name="label" translatable="yes">Plugins</property> |
1211 | - </object> |
1212 | - <packing> |
1213 | - <property name="position">2</property> |
1214 | - <property name="tab_fill">False</property> |
1215 | - </packing> |
1216 | - </child> |
1217 | - </object> |
1218 | + <child type="label"> |
1219 | + <object class="GtkLabel" id="prefs-label4"> |
1220 | + <property name="visible">True</property> |
1221 | + <property name="can_focus">False</property> |
1222 | + <property name="ypad">5</property> |
1223 | + <property name="label" translatable="yes"><b>Task Browser</b></property> |
1224 | + <property name="use_markup">True</property> |
1225 | + </object> |
1226 | + </child> |
1227 | + </object> |
1228 | + <packing> |
1229 | + <property name="expand">False</property> |
1230 | + <property name="fill">True</property> |
1231 | + <property name="position">2</property> |
1232 | + </packing> |
1233 | + </child> |
1234 | + </object> |
1235 | + </child> |
1236 | + <child type="tab"> |
1237 | + <object class="GtkLabel" id="label2"> |
1238 | + <property name="visible">True</property> |
1239 | + <property name="can_focus">False</property> |
1240 | + <property name="label" translatable="yes">page 1</property> |
1241 | + </object> |
1242 | + <packing> |
1243 | + <property name="tab_fill">False</property> |
1244 | + </packing> |
1245 | + </child> |
1246 | + <child> |
1247 | + <placeholder/> |
1248 | + </child> |
1249 | + <child type="tab"> |
1250 | + <object class="GtkLabel" id="label3"> |
1251 | + <property name="visible">True</property> |
1252 | + <property name="can_focus">False</property> |
1253 | + <property name="label" translatable="yes">page 2</property> |
1254 | + </object> |
1255 | + <packing> |
1256 | + <property name="position">1</property> |
1257 | + <property name="tab_fill">False</property> |
1258 | + </packing> |
1259 | + </child> |
1260 | + <child> |
1261 | + <placeholder/> |
1262 | + </child> |
1263 | + <child type="tab"> |
1264 | + <object class="GtkLabel" id="label4"> |
1265 | + <property name="visible">True</property> |
1266 | + <property name="can_focus">False</property> |
1267 | + <property name="label" translatable="yes">page 3</property> |
1268 | + </object> |
1269 | + <packing> |
1270 | + <property name="position">2</property> |
1271 | + <property name="tab_fill">False</property> |
1272 | + </packing> |
1273 | </child> |
1274 | </object> |
1275 | <packing> |
1276 | - <property name="position">1</property> |
1277 | + <property name="expand">True</property> |
1278 | + <property name="fill">True</property> |
1279 | + <property name="position">0</property> |
1280 | </packing> |
1281 | </child> |
1282 | <child internal-child="action_area"> |
1283 | <object class="GtkHButtonBox" id="prefs-action_area"> |
1284 | <property name="visible">True</property> |
1285 | + <property name="can_focus">False</property> |
1286 | <property name="layout_style">end</property> |
1287 | <child> |
1288 | <object class="GtkButton" id="prefs_help"> |
1289 | <property name="label">gtk-help</property> |
1290 | + <property name="can_focus">True</property> |
1291 | + <property name="receives_default">True</property> |
1292 | <property name="no_show_all">True</property> |
1293 | - <property name="can_focus">True</property> |
1294 | - <property name="receives_default">True</property> |
1295 | + <property name="use_action_appearance">False</property> |
1296 | <property name="use_stock">True</property> |
1297 | - <signal name="activate" handler="on_prefs_help"/> |
1298 | + <signal name="activate" handler="on_prefs_help" swapped="no"/> |
1299 | </object> |
1300 | <packing> |
1301 | <property name="expand">False</property> |
1302 | @@ -384,8 +218,9 @@ |
1303 | <property name="visible">True</property> |
1304 | <property name="can_focus">True</property> |
1305 | <property name="receives_default">True</property> |
1306 | + <property name="use_action_appearance">False</property> |
1307 | <property name="use_stock">True</property> |
1308 | - <signal name="released" handler="on_prefs_close"/> |
1309 | + <signal name="released" handler="on_prefs_close" swapped="no"/> |
1310 | </object> |
1311 | <packing> |
1312 | <property name="expand">False</property> |
1313 | @@ -396,6 +231,7 @@ |
1314 | </object> |
1315 | <packing> |
1316 | <property name="expand">False</property> |
1317 | + <property name="fill">True</property> |
1318 | <property name="pack_type">end</property> |
1319 | <property name="position">0</property> |
1320 | </packing> |
1321 | @@ -407,113 +243,4 @@ |
1322 | <action-widget response="0">prefs_close</action-widget> |
1323 | </action-widgets> |
1324 | </object> |
1325 | - <object class="GtkImage" id="pref_img_plugin_conf"> |
1326 | - <property name="visible">True</property> |
1327 | - <property name="stock">gtk-preferences</property> |
1328 | - </object> |
1329 | - <object class="GtkImage" id="pref_img_plugin_about"> |
1330 | - <property name="visible">True</property> |
1331 | - <property name="stock">gtk-about</property> |
1332 | - </object> |
1333 | - <object class="GtkAboutDialog" id="PluginAboutDialog"> |
1334 | - <property name="border_width">5</property> |
1335 | - <property name="window_position">mouse</property> |
1336 | - <property name="type_hint">dialog</property> |
1337 | - <signal name="close" handler="on_PluginAboutDialog_close"/> |
1338 | - <signal name="response" handler="on_PluginAboutDialog_close"/> |
1339 | - <child internal-child="vbox"> |
1340 | - <object class="GtkVBox" id="pa-vbox1"> |
1341 | - <property name="visible">True</property> |
1342 | - <property name="spacing">2</property> |
1343 | - <child> |
1344 | - <object class="GtkFrame" id="pa-frame1"> |
1345 | - <property name="visible">True</property> |
1346 | - <property name="label_xalign">0</property> |
1347 | - <property name="shadow_type">none</property> |
1348 | - <child> |
1349 | - <object class="GtkAlignment" id="pa-alignment1"> |
1350 | - <property name="visible">True</property> |
1351 | - <property name="left_padding">12</property> |
1352 | - <child> |
1353 | - <object class="GtkLabel" id="PluginDepends"> |
1354 | - <property name="visible">True</property> |
1355 | - <property name="use_markup">True</property> |
1356 | - </object> |
1357 | - </child> |
1358 | - </object> |
1359 | - </child> |
1360 | - <child type="label"> |
1361 | - <object class="GtkLabel" id="pa-label1"> |
1362 | - <property name="visible">True</property> |
1363 | - <property name="label" translatable="yes"><b>Dependencies</b></property> |
1364 | - <property name="use_markup">True</property> |
1365 | - </object> |
1366 | - </child> |
1367 | - </object> |
1368 | - <packing> |
1369 | - <property name="position">3</property> |
1370 | - </packing> |
1371 | - </child> |
1372 | - <child internal-child="action_area"> |
1373 | - <object class="GtkHButtonBox" id="pa-action_area1"> |
1374 | - <property name="visible">True</property> |
1375 | - <property name="layout_style">end</property> |
1376 | - </object> |
1377 | - <packing> |
1378 | - <property name="expand">False</property> |
1379 | - <property name="pack_type">end</property> |
1380 | - <property name="position">0</property> |
1381 | - </packing> |
1382 | - </child> |
1383 | - </object> |
1384 | - </child> |
1385 | - </object> |
1386 | - <object class="GtkImage" id="pref_img_plugin"> |
1387 | - <property name="visible">True</property> |
1388 | - <property name="icon_name">gtg-plugin</property> |
1389 | - </object> |
1390 | - <object class="GtkDialog" id="PluginConfigDialog"> |
1391 | - <property name="border_width">5</property> |
1392 | - <property name="window_position">mouse</property> |
1393 | - <property name="type_hint">dialog</property> |
1394 | - <property name="has_separator">False</property> |
1395 | - <child internal-child="vbox"> |
1396 | - <object class="GtkVBox" id="pc-vbox1"> |
1397 | - <property name="visible">True</property> |
1398 | - <property name="spacing">2</property> |
1399 | - <child> |
1400 | - <placeholder/> |
1401 | - </child> |
1402 | - <child internal-child="action_area"> |
1403 | - <object class="GtkHButtonBox" id="pc-action_area1"> |
1404 | - <property name="visible">True</property> |
1405 | - <property name="layout_style">end</property> |
1406 | - <child> |
1407 | - <object class="GtkButton" id="PluginConfigClose"> |
1408 | - <property name="label">gtk-close</property> |
1409 | - <property name="visible">True</property> |
1410 | - <property name="can_focus">True</property> |
1411 | - <property name="receives_default">True</property> |
1412 | - <property name="use_stock">True</property> |
1413 | - <signal name="released" handler="on_PluginConfigClose_released"/> |
1414 | - </object> |
1415 | - <packing> |
1416 | - <property name="expand">False</property> |
1417 | - <property name="fill">False</property> |
1418 | - <property name="position">0</property> |
1419 | - </packing> |
1420 | - </child> |
1421 | - </object> |
1422 | - <packing> |
1423 | - <property name="expand">False</property> |
1424 | - <property name="pack_type">end</property> |
1425 | - <property name="position">0</property> |
1426 | - </packing> |
1427 | - </child> |
1428 | - </object> |
1429 | - </child> |
1430 | - <action-widgets> |
1431 | - <action-widget response="0">PluginConfigClose</action-widget> |
1432 | - </action-widgets> |
1433 | - </object> |
1434 | </interface> |
1435 | |
1436 | === modified file 'GTG/gtk/preferences.py' |
1437 | --- GTG/gtk/preferences.py 2012-05-27 15:33:03 +0000 |
1438 | +++ GTG/gtk/preferences.py 2012-06-07 15:29:21 +0000 |
1439 | @@ -1,7 +1,7 @@ |
1440 | # -*- coding: utf-8 -*- |
1441 | # ----------------------------------------------------------------------------- |
1442 | # Gettings Things Gnome! - a personal organizer for the GNOME desktop |
1443 | -# Copyright (c) 2008-2009 - Lionel Dricot & Bertrand Rousseau |
1444 | +# Copyright (c) 2008-2012 - Lionel Dricot & Bertrand Rousseau |
1445 | # |
1446 | # This program is free software: you can redistribute it and/or modify it under |
1447 | # the terms of the GNU General Public License as published by the Free Software |
1448 | @@ -16,447 +16,136 @@ |
1449 | # You should have received a copy of the GNU General Public License along with |
1450 | # this program. If not, see <http://www.gnu.org/licenses/>. |
1451 | # ----------------------------------------------------------------------------- |
1452 | -""" The Preferences Dialog for loading plugins and configuring GTG """ |
1453 | + |
1454 | +""" The Preferences Dialog for configuring GTG """ |
1455 | + |
1456 | import os |
1457 | import shutil |
1458 | |
1459 | import gtk |
1460 | -import pango |
1461 | from xdg.BaseDirectory import xdg_config_home |
1462 | |
1463 | -from GTG import _ |
1464 | -from GTG.core.plugins import GnomeConfig |
1465 | -from GTG.gtk import ViewConfig |
1466 | -from GTG.core.plugins.engine import PluginEngine |
1467 | - |
1468 | - |
1469 | -__all__ = [ |
1470 | - 'PreferencesDialog', |
1471 | - ] |
1472 | - |
1473 | -# Default plugin information text |
1474 | -PLUGINS_DEFAULT_DESC = _("Click on a plugin name to view its description here.") |
1475 | - |
1476 | -# columns in PreferencesDialog.plugin_store |
1477 | -PLUGINS_COL_ID = 0 |
1478 | -PLUGINS_COL_ENABLED = 1 |
1479 | -PLUGINS_COL_NAME = 2 |
1480 | -PLUGINS_COL_SHORT_DESC = 3 |
1481 | -PLUGINS_COL_DESC = 4 |
1482 | -PLUGINS_COL_ACTIVATABLE = 5 |
1483 | - |
1484 | -def plugin_icon(column, cell, store, iter): |
1485 | - """Callback to set the content of a PluginTree cell. |
1486 | - |
1487 | - See PreferencesDialog._init_plugin_tree(). |
1488 | - |
1489 | - """ |
1490 | - cell.set_property('icon-name', 'gtg-plugin') |
1491 | - cell.set_property('sensitive', store.get_value(iter, |
1492 | - PLUGINS_COL_ACTIVATABLE)) |
1493 | - |
1494 | - |
1495 | -def plugin_markup(column, cell, store, iter, self): |
1496 | - """Callback to set the content of a PluginTree cell. |
1497 | - |
1498 | - See PreferencesDialog._init_plugin_tree(). |
1499 | - |
1500 | - """ |
1501 | - name = store.get_value(iter, PLUGINS_COL_NAME) |
1502 | - desc = store.get_value(iter, PLUGINS_COL_SHORT_DESC) |
1503 | - plugin_id = store.get_value(iter, PLUGINS_COL_ID) |
1504 | - p = self.pengine.get_plugin(plugin_id) |
1505 | - error_text = plugin_error_short_text(p) |
1506 | - if error_text != "": |
1507 | - cell.set_property('markup', "<b>%s</b>\n%s\n<i>%s</i>" % (name, desc, error_text)) |
1508 | - else: |
1509 | - cell.set_property('markup', "<b>%s</b>\n%s" % (name, desc)) |
1510 | - cell.set_property('sensitive', store.get_value(iter, |
1511 | - PLUGINS_COL_ACTIVATABLE)) |
1512 | - |
1513 | -def plugin_error_short_text(plugin): |
1514 | - """ Return small version of description of missing module dependencies |
1515 | - for displaying in plugin markup """ |
1516 | - if not plugin.error: |
1517 | - return "" |
1518 | - |
1519 | - # get lists |
1520 | - modules = plugin.missing_modules |
1521 | - dbus = plugin.missing_dbus |
1522 | - |
1523 | - # convert to strings |
1524 | - if modules: |
1525 | - modules = "<small><b>%s</b></small>" % ', '.join(modules) |
1526 | - if dbus: |
1527 | - ifaces = ["%s:%s" % (a, b) for (a, b) in dbus] |
1528 | - dbus = "<small><b>%s</b></small>" % ', '.join(ifaces) |
1529 | - # combine |
1530 | - if modules and not dbus: |
1531 | - text = '\n'.join((GnomeConfig.miss2, modules)) |
1532 | - elif dbus and not modules: |
1533 | - text = '\n'.join((GnomeConfig.dmiss2, dbus)) |
1534 | - elif modules and dbus: |
1535 | - text = '\n'.join((GnomeConfig.bmiss2, modules, dbus)) |
1536 | - else: |
1537 | - text = "" |
1538 | - return text |
1539 | - |
1540 | -def plugin_error_text(plugin): |
1541 | - """Generate some helpful text about missing module dependencies.""" |
1542 | - if not plugin.error: |
1543 | - return GnomeConfig.CANLOAD |
1544 | - # describe missing dependencies |
1545 | - text = "<b>%s</b>. \n" % GnomeConfig.CANNOTLOAD |
1546 | - # get lists |
1547 | - modules = plugin.missing_modules |
1548 | - dbus = plugin.missing_dbus |
1549 | - # convert to strings |
1550 | - if modules: |
1551 | - modules = "<small><b>%s</b></small>" % ', '.join(modules) |
1552 | - if dbus: |
1553 | - ifaces = ["%s:%s" % (a, b) for (a, b) in dbus] |
1554 | - dbus = "<small><b>%s</b></small>" % ', '.join(ifaces) |
1555 | - # combine |
1556 | - if modules and not dbus: |
1557 | - text += '\n'.join((GnomeConfig.MODULEMISSING, modules)) |
1558 | - elif dbus and not modules: |
1559 | - text += '\n'.join((GnomeConfig.DBUSMISSING, dbus)) |
1560 | - elif modules and dbus: |
1561 | - text += '\n'.join((GnomeConfig.MODULANDDBUS, modules, dbus)) |
1562 | - else: |
1563 | - text += GnomeConfig.UNKNOWN |
1564 | - return text |
1565 | +from GTG import _ |
1566 | +from GTG import info |
1567 | +from GTG.gtk import ViewConfig |
1568 | + |
1569 | +AUTOSTART_DIRECTORY = os.path.join(xdg_config_home, "autostart") |
1570 | +AUTOSTART_FILE = "gtg.desktop" |
1571 | +AUTOSTART_PATH = os.path.join(AUTOSTART_DIRECTORY, AUTOSTART_FILE) |
1572 | + |
1573 | + |
1574 | +def enable_gtg_autostart(): |
1575 | + """ Enable autostart |
1576 | + |
1577 | + Firstly, locate gtg.desktop file. Then link it in AUTOSTART_FILE. |
1578 | + On Windows, there is no os.symlink, just copy the file. """ |
1579 | + desktop_file_path = None |
1580 | + this_directory = os.path.dirname(os.path.abspath(__file__)) |
1581 | + for path in ["../..", "../../../applications", |
1582 | + "../../../../../share/applications"]: |
1583 | + fullpath = os.path.join(this_directory, path, AUTOSTART_FILE) |
1584 | + fullpath = os.path.normpath(fullpath) |
1585 | + if os.path.isfile(fullpath): |
1586 | + desktop_file_path = fullpath |
1587 | + break |
1588 | + |
1589 | + if desktop_file_path: |
1590 | + if not os.path.exists(AUTOSTART_DIRECTORY): |
1591 | + os.mkdir(AUTOSTART_DIRECTORY) |
1592 | + |
1593 | + if os.path.isdir(AUTOSTART_DIRECTORY) and \ |
1594 | + not os.path.exists(AUTOSTART_PATH): |
1595 | + if hasattr(os, "symlink"): |
1596 | + os.symlink(desktop_file_path, AUTOSTART_PATH) |
1597 | + else: |
1598 | + shutil.copyfile(desktop_file_path, AUTOSTART_PATH) |
1599 | + |
1600 | + |
1601 | +def disable_gtg_autostart(): |
1602 | + """ Disable autostart, removing the file in autostart_path """ |
1603 | + if os.path.isfile(AUTOSTART_PATH): |
1604 | + os.remove(AUTOSTART_PATH) |
1605 | |
1606 | |
1607 | class PreferencesDialog: |
1608 | - |
1609 | - __AUTOSTART_DIRECTORY = os.path.join(xdg_config_home, "autostart") |
1610 | - __AUTOSTART_FILE = "gtg.desktop" |
1611 | - |
1612 | - def __init__(self, config_obj, req): |
1613 | - """Constructor.""" |
1614 | - self.config_obj = config_obj |
1615 | + """ Show preference dialog """ |
1616 | + |
1617 | + def __init__(self, req): |
1618 | self.req = req |
1619 | - self.config = self.config_obj.conf_dict |
1620 | - self.builder = gtk.Builder() |
1621 | - self.builder.add_from_file(ViewConfig.PREFERENCES_GLADE_FILE) |
1622 | - # store references to some objects |
1623 | - widgets = { |
1624 | - 'dialog': 'PreferencesDialog', |
1625 | - 'backend_tree': 'BackendTree', |
1626 | - 'plugin_tree': 'PluginTree', |
1627 | - 'plugin_about_dialog': 'PluginAboutDialog', |
1628 | - 'plugin_configure': 'plugin_configure', |
1629 | - 'plugin_depends': 'PluginDepends', |
1630 | - 'plugin_config_dialog': 'PluginConfigDialog', |
1631 | - 'pref_autostart': 'pref_autostart', |
1632 | - 'pref_show_preview': 'pref_show_preview', |
1633 | - 'bg_color_enable': 'bg_color_enable', |
1634 | - } |
1635 | - for attr, widget in widgets.iteritems(): |
1636 | - setattr(self, attr, self.builder.get_object(widget)) |
1637 | - # keep a reference to the parent task browser |
1638 | - self.pengine = PluginEngine() |
1639 | - #plugin config initiation, if never used |
1640 | - if "plugins" in self.config: |
1641 | - if "enabled" not in self.config["plugins"]: |
1642 | - self.config["plugins"]["enabled"] = [] |
1643 | - |
1644 | - if "disabled" not in self.config["plugins"]: |
1645 | - self.config["plugins"]["disabled"] = [] |
1646 | - elif self.pengine.get_plugins(): |
1647 | - self.config["plugins"] = {} |
1648 | - self.config["plugins"]["disabled"] = \ |
1649 | - [p.module_name for p in self.pengine.get_plugins("disabled")] |
1650 | - self.config["plugins"]["enabled"] = \ |
1651 | - [p.module_name for p in self.pengine.get_plugins("enabled")] |
1652 | - # initialize tree models |
1653 | - self._init_backend_tree() |
1654 | - # this can't happen yet, due to the order of things in |
1655 | - # TaskBrowser.__init__(). Happens in activate() instead. |
1656 | - # self._init_plugin_tree() |
1657 | - pref_signals_dic = self.get_signals_dict() |
1658 | - self.builder.connect_signals(pref_signals_dic) |
1659 | - |
1660 | - #this line enables the about dialog widget to be reused |
1661 | - self.plugin_about_dialog.connect("delete-event", lambda w, e: self.plugin_about_dialog.hide() or True) |
1662 | - |
1663 | - def _init_backend_tree(self): |
1664 | - """Initialize the BackendTree gtk.TreeView.""" |
1665 | - self._refresh_backend_store() |
1666 | - # TODO |
1667 | - |
1668 | - def _refresh_backend_store(self): |
1669 | - """Populate a gtk.ListStore with backend information.""" |
1670 | - # create and clear a gtk.ListStore for backend information |
1671 | - if not hasattr(self, 'backend_store'): |
1672 | - # TODO: create the liststore. It should have one column for each |
1673 | - # backend. |
1674 | - self.backend_store = gtk.ListStore(str) |
1675 | - self.backend_store.clear() |
1676 | - # TODO |
1677 | - |
1678 | - def _refresh_plugin_store(self): |
1679 | - """Populate a gtk.ListStore with plugin information.""" |
1680 | - # create and clear a gtk.ListStore |
1681 | - if not hasattr(self, 'plugin_store'): |
1682 | - # see constants PLUGINS_COL_* for column meanings |
1683 | - self.plugin_store = gtk.ListStore(str, 'gboolean', str, str, str, |
1684 | - 'gboolean', ) |
1685 | - self.plugin_store.clear() |
1686 | - # refresh the status of all plugins |
1687 | - self.pengine.recheck_plugin_errors(True) |
1688 | - # repopulate the store |
1689 | - for name, p in self.pengine.plugins.iteritems(): |
1690 | - self.plugin_store.append([name, p.enabled, p.full_name, |
1691 | - p.short_description, p.description, not p.error, ]) # activateable if there is no error |
1692 | - |
1693 | - def _refresh_preferences_store(self): |
1694 | - """Sets the correct value in the preferences checkboxes""" |
1695 | - autostart_path = os.path.join(self.__AUTOSTART_DIRECTORY, \ |
1696 | - self.__AUTOSTART_FILE) |
1697 | - self.pref_autostart.set_active(os.path.isfile(autostart_path)) |
1698 | - |
1699 | - show_preview = self.config_priv.get("contents_preview_enable") |
1700 | - self.pref_show_preview.set_active(show_preview) |
1701 | - |
1702 | - bg_color = self.config_priv.get("bg_color_enable") |
1703 | - self.bg_color_enable.set_active(bg_color) |
1704 | - |
1705 | - def _init_plugin_tree(self): |
1706 | - """Initialize the PluginTree gtk.TreeView. |
1707 | - |
1708 | - The format is modelled after the one used in gedit; see |
1709 | - http://git.gnome.org/browse/gedit/tree/gedit/gedit-plugin-mapnager.c |
1710 | - |
1711 | - """ |
1712 | - # force creation of the gtk.ListStore so we can reference it |
1713 | - self._refresh_plugin_store() |
1714 | - |
1715 | - # renderer for the toggle column |
1716 | - renderer = gtk.CellRendererToggle() |
1717 | - renderer.set_property('xpad', 6) |
1718 | - renderer.connect('toggled', self.on_plugin_toggle) |
1719 | - # toggle column |
1720 | - column = gtk.TreeViewColumn(None, renderer, active=PLUGINS_COL_ENABLED, |
1721 | - activatable=PLUGINS_COL_ACTIVATABLE, |
1722 | - sensitive=PLUGINS_COL_ACTIVATABLE) |
1723 | - self.plugin_tree.append_column(column) |
1724 | - |
1725 | - # plugin name column |
1726 | - column = gtk.TreeViewColumn() |
1727 | - column.set_spacing(6) |
1728 | - # icon renderer for the plugin name column |
1729 | - icon_renderer = gtk.CellRendererPixbuf() |
1730 | - icon_renderer.set_property('stock-size', gtk.ICON_SIZE_SMALL_TOOLBAR) |
1731 | - icon_renderer.set_property('xpad', 3) |
1732 | - column.pack_start(icon_renderer, expand=False) |
1733 | - column.set_cell_data_func(icon_renderer, plugin_icon) |
1734 | - # text renderer for the plugin name column |
1735 | - name_renderer = gtk.CellRendererText() |
1736 | - name_renderer.set_property('ellipsize', pango.ELLIPSIZE_END) |
1737 | - column.pack_start(name_renderer) |
1738 | - column.set_cell_data_func(name_renderer, plugin_markup, self) |
1739 | - |
1740 | - self.plugin_tree.append_column(column) |
1741 | - |
1742 | - # finish setup |
1743 | - self.plugin_tree.set_model(self.plugin_store) |
1744 | - self.plugin_tree.set_search_column(2) |
1745 | - |
1746 | - ## GTK signals & related functions |
1747 | - def get_signals_dict(self): |
1748 | - """A dictionary of signals and functions to be connected.""" |
1749 | - SIGNAL_CONNECTIONS_DIC = { |
1750 | -# 'on_preferences_activate': |
1751 | -# self.activate, |
1752 | - # buttons in the dialog itself |
1753 | - 'on_prefs_close': |
1754 | - self.on_close, |
1755 | - 'on_prefs_help': |
1756 | - self.on_help, |
1757 | - # preferences on the Tasks tab |
1758 | + self.config = self.req.get_config('browser') |
1759 | + builder = gtk.Builder() |
1760 | + builder.add_from_file(ViewConfig.PREFERENCES_GLADE_FILE) |
1761 | + |
1762 | + self.dialog = builder.get_object("PreferencesDialog") |
1763 | + self.dialog.set_title(_("Preferences - %s" % info.NAME)) |
1764 | + self.pref_autostart = builder.get_object("pref_autostart") |
1765 | + self.pref_show_preview = builder.get_object("pref_show_preview") |
1766 | + self.bg_color_enable = builder.get_object("bg_color_enable") |
1767 | + |
1768 | + builder.connect_signals({ |
1769 | + 'on_pref_autostart_toggled': |
1770 | + self.on_autostart_toggled, |
1771 | 'on_pref_show_preview_toggled': |
1772 | self.toggle_preview, |
1773 | 'on_bg_color_toggled': |
1774 | self.on_bg_color_toggled, |
1775 | - 'on_pref_check_spelling_toggled': |
1776 | - self.toggle_spellcheck, |
1777 | - # buttons on the Plugins tab |
1778 | - 'on_PluginTree_cursor_changed': |
1779 | - self.on_plugin_select, |
1780 | - 'on_plugin_about': |
1781 | - self.on_plugin_about, |
1782 | - 'on_plugin_configure': |
1783 | - self.on_plugin_configure, |
1784 | - # the PluginAboutDialog |
1785 | - 'on_PluginAboutDialog_close': |
1786 | - self.on_plugin_about_close, |
1787 | - 'on_PluginAboutDialog_response': |
1788 | - self.on_plugin_about_close, |
1789 | - # the PluginConfigDialog |
1790 | - 'on_PluginConfigClose_released': |
1791 | - self.on_plugin_config_close, |
1792 | + 'on_prefs_help': |
1793 | + self.on_help, |
1794 | + 'on_prefs_close': |
1795 | + self.on_close, |
1796 | 'on_PreferencesDialog_delete_event': |
1797 | self.on_close, |
1798 | - 'on_pref_autostart_toggled': |
1799 | - self.on_autostart_toggled, |
1800 | - } |
1801 | - return SIGNAL_CONNECTIONS_DIC |
1802 | - |
1803 | - def activate(self, config_priv, widget=None): |
1804 | - """Activate the preferences dialog.""" |
1805 | - self.config_priv = config_priv |
1806 | - if len(self.plugin_tree.get_columns()) == 0: |
1807 | - # late setup of PluginTree |
1808 | - self._init_plugin_tree() |
1809 | - else: |
1810 | - self._refresh_plugin_store() |
1811 | - self._refresh_backend_store() |
1812 | + }) |
1813 | + |
1814 | + def _refresh_preferences_store(self): |
1815 | + """ Sets the correct value in the preferences checkboxes """ |
1816 | + has_autostart = os.path.isfile(AUTOSTART_PATH) |
1817 | + self.pref_autostart.set_active(has_autostart) |
1818 | + |
1819 | + show_preview = self.config.get("contents_preview_enable") |
1820 | + self.pref_show_preview.set_active(show_preview) |
1821 | + |
1822 | + bg_color = self.config.get("bg_color_enable") |
1823 | + self.bg_color_enable.set_active(bg_color) |
1824 | + |
1825 | + def _refresh_task_browser(self): |
1826 | + """ Refresh tasks in task browser """ |
1827 | + task_tree = self.req.get_tasks_tree(refresh=False).get_basetree() |
1828 | + task_tree.refresh_all() |
1829 | + |
1830 | + def activate(self): |
1831 | + """ Activate the preferences dialog.""" |
1832 | self._refresh_preferences_store() |
1833 | - self.dialog.present() |
1834 | self.dialog.show_all() |
1835 | |
1836 | - def on_close(self, widget, data = None): |
1837 | - """Close the preferences dialog.""" |
1838 | - |
1839 | + def on_close(self, widget, data=None): # pylint: disable-msg=W0613 |
1840 | + """ Close the preferences dialog.""" |
1841 | self.dialog.hide() |
1842 | return True |
1843 | |
1844 | - def on_help(self, widget): |
1845 | - """Provide help for the preferences dialog.""" |
1846 | + @classmethod |
1847 | + def on_help(cls, widget): # pylint: disable-msg=W0613 |
1848 | + """ In future, this will open help for preferences """ |
1849 | return True |
1850 | |
1851 | - def on_plugin_about(self, widget): |
1852 | - """Display information about a plugin.""" |
1853 | - _, iterator = self.plugin_tree.get_selection().get_selected() |
1854 | - if iterator is None: |
1855 | - return |
1856 | - plugin_id = self.plugin_store.get_value(iterator, PLUGINS_COL_ID) |
1857 | - p = self.pengine.get_plugin(plugin_id) |
1858 | - |
1859 | - pad = self.plugin_about_dialog |
1860 | - pad.set_name(p.full_name) |
1861 | - pad.set_version(p.version) |
1862 | - authors = p.authors |
1863 | - if isinstance(authors, str): |
1864 | - authors = [authors, ] |
1865 | - pad.set_authors(authors) |
1866 | - pad.set_comments(p.description.replace(r'\n', "\n")) |
1867 | - self.plugin_depends.set_label(plugin_error_text(p)) |
1868 | - pad.show_all() |
1869 | - |
1870 | - def on_plugin_about_close(self, widget, *args): |
1871 | - """Close the PluginAboutDialog.""" |
1872 | - self.plugin_about_dialog.hide() |
1873 | - |
1874 | - def on_plugin_configure(self, widget): |
1875 | - """Configure a plugin.""" |
1876 | - _, iterator = self.plugin_tree.get_selection().get_selected() |
1877 | - if iterator is None: |
1878 | - return |
1879 | - plugin_id = self.plugin_store.get_value(iterator, PLUGINS_COL_ID) |
1880 | - # TODO: load plugin's configuration UI and insert into pc-vbox1 in |
1881 | - # position 0. Something like... |
1882 | - #pcd = self.plugin_config_dialog |
1883 | - #pcd.show_all() |
1884 | - # ...for now, use existing code. |
1885 | - plugin = self.pengine.get_plugin(plugin_id) |
1886 | - plugin.instance.configure_dialog(self.dialog) |
1887 | - |
1888 | - def on_plugin_config_close(self, widget): |
1889 | - """Close the PluginConfigDialog.""" |
1890 | - self.plugin_config_dialog.hide() |
1891 | - |
1892 | - def on_plugin_select(self, plugin_tree): |
1893 | - """ Callback when user select/unselect a plugin |
1894 | - |
1895 | - Update the button "Configure plugin" sensitivity """ |
1896 | - model, iterator = plugin_tree.get_selection().get_selected() |
1897 | - if iterator is not None: |
1898 | - plugin_id = model.get_value(iterator, PLUGINS_COL_ID) |
1899 | - plugin = self.pengine.get_plugin(plugin_id) |
1900 | - self._update_plugin_configure(plugin) |
1901 | - |
1902 | - def on_plugin_toggle(self, widget, path): |
1903 | - """Toggle a plugin enabled/disabled.""" |
1904 | - iter = self.plugin_store.get_iter(path) |
1905 | - plugin_id = self.plugin_store.get_value(iter, PLUGINS_COL_ID) |
1906 | - p = self.pengine.get_plugin(plugin_id) |
1907 | - p.enabled = not self.plugin_store.get_value(iter, PLUGINS_COL_ENABLED) |
1908 | - if p.enabled: |
1909 | - self.pengine.activate_plugins([p]) |
1910 | - self.config["plugins"]["enabled"].append(p.module_name) |
1911 | - if p.module_name in self.config["plugins"]["disabled"]: |
1912 | - self.config["plugins"]["disabled"].remove(p.module_name) |
1913 | + @classmethod |
1914 | + def on_autostart_toggled(cls, widget): |
1915 | + """ Toggle GTG autostarting with the GNOME desktop """ |
1916 | + if widget.get_active(): |
1917 | + enable_gtg_autostart() |
1918 | else: |
1919 | - self.pengine.deactivate_plugins([p]) |
1920 | - self.config["plugins"]["disabled"].append(p.module_name) |
1921 | - if p.module_name in self.config["plugins"]["enabled"]: |
1922 | - self.config["plugins"]["enabled"].remove(p.module_name) |
1923 | - self.plugin_store.set_value(iter, PLUGINS_COL_ENABLED, p.enabled) |
1924 | - self._update_plugin_configure(p) |
1925 | - |
1926 | - self.config_obj.save() |
1927 | + disable_gtg_autostart() |
1928 | |
1929 | def toggle_preview(self, widget): |
1930 | - """Toggle previews in the task view on or off.""" |
1931 | - curstate = self.config_priv.get("contents_preview_enable") |
1932 | + """ Toggle previews in the task view on or off.""" |
1933 | + curstate = self.config.get("contents_preview_enable") |
1934 | if curstate != widget.get_active(): |
1935 | - self.config_priv.set("contents_preview_enable", not curstate) |
1936 | - view = self.req.get_tasks_tree(refresh=False) |
1937 | - view.refresh_all() |
1938 | + self.config.set("contents_preview_enable", not curstate) |
1939 | + self._refresh_task_browser() |
1940 | |
1941 | def on_bg_color_toggled(self, widget): |
1942 | """ Save configuration and refresh nodes to apply the change """ |
1943 | - curstate = self.config_priv.get("bg_color_enable") |
1944 | + curstate = self.config.get("bg_color_enable") |
1945 | if curstate != widget.get_active(): |
1946 | - self.config_priv.set("bg_color_enable", not curstate) |
1947 | - task_tree = self.req.get_tasks_tree(refresh=False).get_basetree() |
1948 | - task_tree.refresh_all() |
1949 | - |
1950 | - def toggle_spellcheck(self, widget): |
1951 | - """Toggle spell checking on or off.""" |
1952 | - print __name__ |
1953 | - |
1954 | - def _update_plugin_configure(self, plugin): |
1955 | - """ Enable the button "Configure Plugin" appropriate. """ |
1956 | - configurable = plugin.active and plugin.is_configurable() |
1957 | - self.plugin_configure.set_property('sensitive', configurable) |
1958 | - |
1959 | - def on_autostart_toggled(self, widget): |
1960 | - """Toggle GTG autostarting with the GNOME desktop""" |
1961 | - autostart_path = os.path.join(self.__AUTOSTART_DIRECTORY, \ |
1962 | - self.__AUTOSTART_FILE) |
1963 | - if widget.get_active() == False: |
1964 | - #Disable autostart, removing the file in autostart_path |
1965 | - if os.path.isfile(autostart_path): |
1966 | - os.remove(autostart_path) |
1967 | - else: |
1968 | - #Enable autostart |
1969 | - #We look for the desktop file |
1970 | - desktop_file_path = None |
1971 | - desktop_file_directories = ["../..", |
1972 | - "../../../applications", |
1973 | - "../../../../../share/applications"] |
1974 | - this_directory = os.path.dirname(os.path.abspath(__file__)) |
1975 | - for path in desktop_file_directories: |
1976 | - fullpath = os.path.normpath(os.path.join(this_directory, path, \ |
1977 | - self.__AUTOSTART_FILE)) |
1978 | - if os.path.isfile(fullpath): |
1979 | - desktop_file_path = fullpath |
1980 | - break |
1981 | - #If we have found the desktop file, we make a link to in in |
1982 | - # autostart_path. If symbolic linking is not possible |
1983 | - # (that is, if we are running on Windows), then copy the file |
1984 | - if desktop_file_path: |
1985 | - if not os.path.exists(self.__AUTOSTART_DIRECTORY): |
1986 | - os.mkdir(self.__AUTOSTART_DIRECTORY) |
1987 | - if os.path.isdir(self.__AUTOSTART_DIRECTORY) and \ |
1988 | - not os.path.exists(autostart_path): |
1989 | - if hasattr(os, "symlink"): |
1990 | - os.symlink(desktop_file_path, \ |
1991 | - autostart_path) |
1992 | - else: |
1993 | - shutil.copyfile(desktop_file_path, \ |
1994 | - autostart_path) |
1995 | + self.config.set("bg_color_enable", not curstate) |
1996 | + self._refresh_task_browser() |
It runs fine. I haven't checked the code yet.
Small remarks:
- I would add some padding around the widget (maybe 5-10 pixels) in order to give a better look to the dialogs
- "Preferences" is usually the last item of the Edit menu, so I would move it there. Also there is usually a separator item, I would add one too. That would give:
* Plugins
* Synchronization Services
* --------- (separator)
* Preferences