Code to make it easier to experiment
[gc-dialer] / src / hildonize.py
1 #!/usr/bin/env python
2
3
4 import gobject
5 import gtk
6 import dbus
7
8
9 class _NullHildonModule(object):
10         pass
11
12
13 try:
14         import hildon as _hildon
15         hildon  = _hildon # Dumb but gets around pyflakiness
16 except (ImportError, OSError):
17         hildon = _NullHildonModule
18
19
20 IS_HILDON_SUPPORTED = hildon is not _NullHildonModule
21
22
23 class _NullHildonProgram(object):
24
25         def add_window(self, window):
26                 pass
27
28
29 def _hildon_get_app_class():
30         return hildon.Program
31
32
33 def _null_get_app_class():
34         return _NullHildonProgram
35
36
37 if IS_HILDON_SUPPORTED:
38         get_app_class = _hildon_get_app_class
39 else:
40         get_app_class = _null_get_app_class
41
42
43 def _hildon_set_application_title(window, title):
44         pass
45
46
47 def _null_set_application_title(window, title):
48         window.set_title(title)
49
50
51 if IS_HILDON_SUPPORTED:
52         set_application_title = _hildon_set_application_title
53 else:
54         set_application_title = _null_set_application_title
55
56
57 def _fremantle_hildonize_window(app, window):
58         oldWindow = window
59         newWindow = hildon.StackableWindow()
60         oldWindow.get_child().reparent(newWindow)
61         app.add_window(newWindow)
62         return newWindow
63
64
65 def _hildon_hildonize_window(app, window):
66         oldWindow = window
67         newWindow = hildon.Window()
68         oldWindow.get_child().reparent(newWindow)
69         app.add_window(newWindow)
70         return newWindow
71
72
73 def _null_hildonize_window(app, window):
74         return window
75
76
77 try:
78         hildon.StackableWindow
79         hildonize_window = _fremantle_hildonize_window
80 except AttributeError:
81         try:
82                 hildon.Window
83                 hildonize_window = _hildon_hildonize_window
84         except AttributeError:
85                 hildonize_window = _null_hildonize_window
86
87
88 def _fremantle_hildonize_menu(window, gtkMenu, buttons):
89         appMenu = hildon.AppMenu()
90         for button in buttons:
91                 appMenu.append(button)
92         window.set_app_menu(appMenu)
93         gtkMenu.get_parent().remove(gtkMenu)
94         return appMenu
95
96
97 def _hildon_hildonize_menu(window, gtkMenu, ignoredButtons):
98         hildonMenu = gtk.Menu()
99         for child in gtkMenu.get_children():
100                 child.reparent(hildonMenu)
101         window.set_menu(hildonMenu)
102         gtkMenu.destroy()
103         return hildonMenu
104
105
106 def _null_hildonize_menu(window, gtkMenu, ignoredButtons):
107         return gtkMenu
108
109
110 try:
111         hildon.AppMenu
112         GTK_MENU_USED = False
113         hildonize_menu = _fremantle_hildonize_menu
114 except AttributeError:
115         GTK_MENU_USED = True
116         if IS_HILDON_SUPPORTED:
117                 hildonize_menu = _hildon_hildonize_menu
118         else:
119                 hildonize_menu = _null_hildonize_menu
120
121
122 def _hildon_set_cell_thumb_selectable(renderer):
123         renderer.set_property("scale", 1.5)
124
125
126 def _null_set_cell_thumb_selectable(renderer):
127         pass
128
129
130 if IS_HILDON_SUPPORTED:
131         set_cell_thumb_selectable = _hildon_set_cell_thumb_selectable
132 else:
133         set_cell_thumb_selectable = _null_set_cell_thumb_selectable
134
135
136 def _hildon_hildonize_text_entry(textEntry):
137         textEntry.set_property('hildon-input-mode', 7)
138
139
140 def _null_hildonize_text_entry(textEntry):
141         pass
142
143
144 if IS_HILDON_SUPPORTED:
145         hildonize_text_entry = _hildon_hildonize_text_entry
146 else:
147         hildonize_text_entry = _null_hildonize_text_entry
148
149
150 def _hildon_mark_window_rotatable(window):
151         # gtk documentation is unclear whether this does a "=" or a "|="
152         window.set_flags(hildon.HILDON_PORTRAIT_MODE_SUPPORT)
153
154
155 def _null_mark_window_rotatable(window):
156         pass
157
158
159 try:
160         hildon.HILDON_PORTRAIT_MODE_SUPPORT
161         mark_window_rotatable = _hildon_mark_window_rotatable
162 except AttributeError:
163         mark_window_rotatable = _null_mark_window_rotatable
164
165
166 def _hildon_window_to_portrait(window):
167         # gtk documentation is unclear whether this does a "=" or a "|="
168         window.set_flags(hildon.HILDON_PORTRAIT_MODE_SUPPORT)
169
170
171 def _hildon_window_to_landscape(window):
172         # gtk documentation is unclear whether this does a "=" or a "&= ~"
173         window.unset_flags(hildon.HILDON_PORTRAIT_MODE_REQUEST)
174
175
176 def _null_window_to_portrait(window):
177         pass
178
179
180 def _null_window_to_landscape(window):
181         pass
182
183
184 try:
185         hildon.HILDON_PORTRAIT_MODE_SUPPORT
186         hildon.HILDON_PORTRAIT_MODE_REQUEST
187
188         window_to_portrait = _hildon_window_to_portrait
189         window_to_landscape = _hildon_window_to_landscape
190 except AttributeError:
191         window_to_portrait = _null_window_to_portrait
192         window_to_landscape = _null_window_to_landscape
193
194
195 def get_device_orientation():
196         bus = dbus.SystemBus()
197         try:
198                 rawMceRequest = bus.get_object("com.nokia.mce", "/com/nokia/mce/request")
199                 mceRequest = dbus.Interface(rawMceRequest, dbus_interface="com.nokia.mce.request")
200                 orientation, standState, faceState, xAxis, yAxis, zAxis = mceRequest.get_device_orientation()
201         except dbus.exception.DBusException:
202                 # catching for documentation purposes that when a system doesn't
203                 # support this, this is what to expect
204                 raise
205
206         if orientation == "":
207                 return gtk.ORIENTATION_HORIZONTAL
208         elif orientation == "":
209                 return gtk.ORIENTATION_VERTICAL
210         else:
211                 raise RuntimeError("Unknown orientation: %s" % orientation)
212
213
214 def _hildon_hildonize_password_entry(textEntry):
215         textEntry.set_property('hildon-input-mode', 7 | (1 << 29))
216
217
218 def _null_hildonize_password_entry(textEntry):
219         pass
220
221
222 if IS_HILDON_SUPPORTED:
223         hildonize_password_entry = _hildon_hildonize_password_entry
224 else:
225         hildonize_password_entry = _null_hildonize_password_entry
226
227
228 def _hildon_hildonize_combo_entry(comboEntry):
229         comboEntry.set_property('hildon-input-mode', 1 << 4)
230
231
232 def _null_hildonize_combo_entry(textEntry):
233         pass
234
235
236 if IS_HILDON_SUPPORTED:
237         hildonize_combo_entry = _hildon_hildonize_combo_entry
238 else:
239         hildonize_combo_entry = _null_hildonize_combo_entry
240
241
242 def _fremantle_hildonize_scrollwindow(scrolledWindow):
243         pannableWindow = hildon.PannableArea()
244
245         child = scrolledWindow.get_child()
246         scrolledWindow.remove(child)
247         pannableWindow.add(child)
248
249         parent = scrolledWindow.get_parent()
250         parent.remove(scrolledWindow)
251         parent.add(pannableWindow)
252
253         return pannableWindow
254
255
256 def _hildon_hildonize_scrollwindow(scrolledWindow):
257         hildon.hildon_helper_set_thumb_scrollbar(scrolledWindow, True)
258         return scrolledWindow
259
260
261 def _null_hildonize_scrollwindow(scrolledWindow):
262         return scrolledWindow
263
264
265 try:
266         hildon.PannableArea
267         hildonize_scrollwindow = _fremantle_hildonize_scrollwindow
268         hildonize_scrollwindow_with_viewport = _hildon_hildonize_scrollwindow
269 except AttributeError:
270         try:
271                 hildon.hildon_helper_hildonize_scrollwindow
272                 hildonize_scrollwindow = _hildon_hildonize_scrollwindow
273                 hildonize_scrollwindow_with_viewport = _hildon_hildonize_scrollwindow
274         except AttributeError:
275                 hildonize_scrollwindow = _null_hildonize_scrollwindow
276                 hildonize_scrollwindow_with_viewport = _null_hildonize_scrollwindow
277
278
279 def _hildon_request_number(parent, title, range, default):
280         spinner = hildon.NumberEditor(*range)
281         spinner.set_value(default)
282
283         dialog = gtk.Dialog(
284                 title,
285                 parent,
286                 gtk.DIALOG_MODAL|gtk.DIALOG_DESTROY_WITH_PARENT,
287                 (gtk.STOCK_OK, gtk.RESPONSE_OK, gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL),
288         )
289         dialog.set_default_response(gtk.RESPONSE_CANCEL)
290         dialog.get_child().add(spinner)
291
292         try:
293                 dialog.show_all()
294                 response = dialog.run()
295         finally:
296                 dialog.hide()
297
298         if response == gtk.RESPONSE_OK:
299                 return spinner.get_value()
300         elif response == gtk.RESPONSE_CANCEL or response == gtk.RESPONSE_DELETE_EVENT:
301                 raise RuntimeError("User cancelled request")
302         else:
303                 raise RuntimeError("Unrecognized response %r", response)
304
305
306 def _null_request_number(parent, title, range, default):
307         adjustment = gtk.Adjustment(default, range[0], range[1], 1, 5, 0)
308         spinner = gtk.SpinButton(adjustment, 0, 0)
309         spinner.set_wrap(False)
310
311         dialog = gtk.Dialog(
312                 title,
313                 parent,
314                 gtk.DIALOG_MODAL|gtk.DIALOG_DESTROY_WITH_PARENT,
315                 (gtk.STOCK_OK, gtk.RESPONSE_OK, gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL),
316         )
317         dialog.set_default_response(gtk.RESPONSE_CANCEL)
318         dialog.get_child().add(spinner)
319
320         try:
321                 dialog.show_all()
322                 response = dialog.run()
323         finally:
324                 dialog.hide()
325
326         if response == gtk.RESPONSE_OK:
327                 return spinner.get_value_as_int()
328         elif response == gtk.RESPONSE_CANCEL or response == gtk.RESPONSE_DELETE_EVENT:
329                 raise RuntimeError("User cancelled request")
330         else:
331                 raise RuntimeError("Unrecognized response %r", response)
332
333
334 try:
335         hildon.NumberEditor # TODO deprecated in fremantle
336         request_number = _hildon_request_number
337 except AttributeError:
338         request_number = _null_request_number
339
340
341 def _hildon_touch_selector(parent, title, items, defaultIndex):
342         model = gtk.ListStore(gobject.TYPE_STRING)
343         for item in items:
344                 model.append((item, ))
345
346         selector = hildon.TouchSelector()
347         selector.append_text_column(model, True)
348         selector.set_column_selection_mode(hildon.TOUCH_SELECTOR_SELECTION_MODE_SINGLE)
349         selector.set_active(0, defaultIndex)
350
351         dialog = hildon.PickerDialog(parent)
352         dialog.set_selector(selector)
353
354         try:
355                 dialog.show_all()
356                 response = dialog.run()
357         finally:
358                 dialog.hide()
359
360         if response == gtk.RESPONSE_OK:
361                 return selector.get_active(0)
362         elif response == gtk.RESPONSE_CANCEL or response == gtk.RESPONSE_DELETE_EVENT:
363                 raise RuntimeError("User cancelled request")
364         else:
365                 raise RuntimeError("Unrecognized response %r", response)
366
367
368 def _null_touch_selector(parent, title, items, defaultIndex = -1):
369         model = gtk.ListStore(gobject.TYPE_STRING)
370         for item in items:
371                 model.append((item, ))
372
373         cell = gtk.CellRendererText()
374
375         combo = gtk.ComboBox()
376         combo.set_model(model)
377         combo.pack_start(cell, True)
378         combo.add_attribute(cell, 'text', 0)
379         combo.set_active(defaultIndex)
380
381         dialog = gtk.Dialog(
382                 title,
383                 parent,
384                 gtk.DIALOG_MODAL|gtk.DIALOG_DESTROY_WITH_PARENT,
385                 (gtk.STOCK_OK, gtk.RESPONSE_OK, gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL),
386         )
387         dialog.set_default_response(gtk.RESPONSE_CANCEL)
388         dialog.get_child().add(combo)
389
390         try:
391                 dialog.show_all()
392                 response = dialog.run()
393         finally:
394                 dialog.hide()
395
396         if response == gtk.RESPONSE_OK:
397                 return combo.get_active()
398         elif response == gtk.RESPONSE_CANCEL or response == gtk.RESPONSE_DELETE_EVENT:
399                 raise RuntimeError("User cancelled request")
400         else:
401                 raise RuntimeError("Unrecognized response %r", response)
402
403
404 try:
405         hildon.PickerDialog
406         hildon.TouchSelector
407         touch_selector = _hildon_touch_selector
408 except AttributeError:
409         touch_selector = _null_touch_selector
410
411
412 if __name__ == "__main__":
413         app = get_app_class()()
414         win = gtk.Window()
415         win = hildonize_window(app, win)
416         if True:
417                 print touch_selector(win, "Test", ["1", "2", "3", "4"], 2)