Contents of /trunk/src/main.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 271 - (hide annotations)
Thu Aug 27 06:24:55 2009 UTC (14 years, 9 months ago) by harbaum
File MIME type: text/plain
File size: 51753 byte(s)
Fixed track update bug
1 harbaum 1 /*
2 harbaum 249 * Copyright (C) 2008-2009 Till Harbaum <till@harbaum.org>.
3 achadwick 101 *
4 harbaum 1 * This file is part of OSM2Go.
5     *
6     * OSM2Go is free software: you can redistribute it and/or modify
7     * it under the terms of the GNU General Public License as published by
8     * the Free Software Foundation, either version 3 of the License, or
9     * (at your option) any later version.
10     *
11     * OSM2Go is distributed in the hope that it will be useful,
12     * but WITHOUT ANY WARRANTY; without even the implied warranty of
13     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14     * GNU General Public License for more details.
15     *
16     * You should have received a copy of the GNU General Public License
17     * along with OSM2Go. If not, see <http://www.gnu.org/licenses/>.
18     */
19    
20     #include <stdio.h>
21     #include <string.h>
22    
23     #include <curl/curl.h>
24 harbaum 22 #include <gdk/gdkkeysyms.h>
25 harbaum 1
26 harbaum 188 #if defined(USE_HILDON) && (MAEMO_VERSION_MAJOR == 5)
27     #include <hildon/hildon-button.h>
28     #include <hildon/hildon-check-button.h>
29     #include <hildon/hildon-window-stack.h>
30 harbaum 190 #include <gdk/gdkx.h>
31     #include <X11/Xatom.h>
32 harbaum 188 #endif
33    
34 harbaum 1 #include "appdata.h"
35 achadwick 28 #include "banner.h"
36 harbaum 1
37     /* disable/enable main screen control dependant on presence of open project */
38 harbaum 218 void main_ui_enable(appdata_t *appdata) {
39 harbaum 4 gboolean project_valid = (appdata->project != NULL);
40     gboolean osm_valid = (appdata->osm != NULL);
41 harbaum 1
42     /* cancel any action in progress */
43     if(GTK_WIDGET_FLAGS(appdata->iconbar->cancel) & GTK_SENSITIVE)
44     map_action_cancel(appdata);
45    
46     /* ---- set project name as window title ----- */
47 harbaum 176 #if defined(USE_HILDON) && MAEMO_VERSION_MAJOR < 5
48     if(project_valid)
49     gtk_window_set_title(GTK_WINDOW(appdata->window), appdata->project->name);
50     else
51     gtk_window_set_title(GTK_WINDOW(appdata->window), "");
52     #else
53 harbaum 1 char *str = NULL;
54 harbaum 227 #ifdef USE_HILDON
55 harbaum 4 if(project_valid)
56 harbaum 245 str = g_markup_printf_escaped("<b>%s</b> - OSM2Go",
57 harbaum 225 appdata->project->name);
58 harbaum 1 else
59 harbaum 225 str = g_markup_printf_escaped("OSM2Go");
60    
61     hildon_window_set_markup(HILDON_WINDOW(appdata->window), str);
62 harbaum 227 #else
63     if(project_valid)
64 harbaum 245 str = g_strdup_printf("%s - OSM2Go", appdata->project->name);
65 harbaum 227 else
66     str = g_strdup_printf("OSM2Go");
67    
68     gtk_window_set_title(GTK_WINDOW(appdata->window), str);
69     #endif
70 harbaum 1 g_free(str);
71     #endif
72    
73     if(appdata->iconbar && appdata->iconbar->toolbar)
74 harbaum 4 gtk_widget_set_sensitive(appdata->iconbar->toolbar, osm_valid);
75 harbaum 1 /* disable all menu entries related to map */
76 harbaum 188 gtk_widget_set_sensitive(appdata->submenu_map, project_valid);
77     gtk_widget_set_sensitive(appdata->menu_item_map_upload, osm_valid);
78     if(appdata->menu_item_map_undo)
79     gtk_widget_set_sensitive(appdata->menu_item_map_undo, osm_valid);
80 harbaum 244 if(appdata->menu_item_map_save_changes)
81     gtk_widget_set_sensitive(appdata->menu_item_map_save_changes, osm_valid);
82 harbaum 188 gtk_widget_set_sensitive(appdata->menu_item_map_undo_changes, osm_valid);
83     gtk_widget_set_sensitive(appdata->menu_item_map_relations, osm_valid);
84     gtk_widget_set_sensitive(appdata->track.submenu_track, osm_valid);
85     gtk_widget_set_sensitive(appdata->submenu_view, osm_valid);
86     gtk_widget_set_sensitive(appdata->submenu_wms, osm_valid);
87 harbaum 1
88 harbaum 195 #ifdef ZOOM_BUTTONS
89     gtk_widget_set_sensitive(appdata->btn_zoom_in, osm_valid);
90     gtk_widget_set_sensitive(appdata->btn_zoom_out, osm_valid);
91     #endif
92    
93 harbaum 4 if(!project_valid)
94 achadwick 6 statusbar_set(appdata, _("Please load or create a project"), FALSE);
95 harbaum 1 }
96    
97     /******************** begin of menu *********************/
98    
99     static void
100 harbaum 139 cb_menu_project_open(GtkMenuItem *item, gpointer data) {
101 harbaum 1 appdata_t *appdata = (appdata_t*)data;
102     project_load(appdata, NULL);
103 harbaum 4 main_ui_enable(appdata);
104 harbaum 1 }
105    
106     static void
107 harbaum 185 cb_menu_project_wizard(GtkMenuItem *item, gpointer data) {
108 harbaum 1 appdata_t *appdata = (appdata_t*)data;
109 harbaum 185 project_wizard(appdata);
110 harbaum 1 }
111    
112 harbaum 266 typedef struct {
113     appdata_t *appdata;
114     GtkWidget *dialog;
115     } about_context_t;
116    
117     #ifdef ENABLE_BROWSER_INTERFACE
118     #ifndef USE_HILDON
119     #include <libgnome/gnome-url.h>
120     #else
121     #include <tablet-browser-interface.h>
122     #endif
123    
124     void on_paypal_button_clicked(GtkButton *button, about_context_t *context) {
125     const char *url =
126     "https://www.paypal.com/cgi-bin/webscr"
127     "?cmd=_s-xclick&hosted_button_id=7439286";
128    
129     #ifndef USE_HILDON
130     /* taken from gnome-open, part of libgnome */
131     GError *err = NULL;
132     gnome_url_show(url, &err);
133     #else
134     /* close the dialog on hildon as it doesn't like open dialogs */
135     gtk_dialog_response(GTK_DIALOG(context->dialog), GTK_RESPONSE_ACCEPT);
136    
137     osso_rpc_run_with_defaults(context->appdata->osso_context, "osso_browser",
138     OSSO_BROWSER_OPEN_NEW_WINDOW_REQ, NULL,
139     DBUS_TYPE_STRING, url,
140     DBUS_TYPE_BOOLEAN, FALSE, DBUS_TYPE_INVALID);
141     #endif
142     }
143     #endif
144    
145 harbaum 1 static void
146 harbaum 139 cb_menu_about(GtkMenuItem *item, gpointer data) {
147 harbaum 266 about_context_t context;
148     context.appdata = (appdata_t *)data;
149 harbaum 1
150     const gchar *authors[] = {
151     "Till Harbaum <till@harbaum.org>",
152 achadwick 28 "Andrew Chadwick <andrewc-osm2go@piffle.org>",
153 harbaum 200 "Marcus Bauer <marcus.bauer@gmail.com>",
154     "John Stowers <john.stowers@gmail.com>",
155 harbaum 1 NULL };
156    
157 harbaum 139 const gchar *artists[] = {
158 harbaum 140 "Andrew Zhilin <drew.zhilin@gmail.com>",
159 harbaum 139 NULL };
160 harbaum 1
161 harbaum 266 context.dialog = g_object_new(GTK_TYPE_ABOUT_DIALOG,
162 harbaum 140 "name", "OSM2Go",
163 harbaum 139 "version", VERSION,
164     "copyright", _("Copyright 2008-2009"),
165     "authors", authors,
166     "artists", artists,
167     "website", _("http://www.harbaum.org/till/maemo"),
168     "comments", _("Mobile OSM Editor"),
169     NULL);
170 harbaum 266
171     #ifdef ENABLE_BROWSER_INTERFACE
172     /* add a way to donate to the project */
173     GtkWidget *alignment = gtk_alignment_new(0.5, 0, 0, 0);
174    
175     GtkWidget *hbox = gtk_hbox_new(FALSE, 8);
176     gtk_box_pack_start(GTK_BOX(hbox),
177     gtk_label_new(_("Do you ĺike OSM2Go?")),
178     FALSE, FALSE, 0);
179    
180     GtkWidget *button = gtk_button_new();
181     gtk_button_set_image(GTK_BUTTON(button),
182     icon_widget_load(&context.appdata->icon, "paypal"));
183     gtk_button_set_relief(GTK_BUTTON(button), GTK_RELIEF_NONE);
184     g_signal_connect(button, "clicked",
185     G_CALLBACK(on_paypal_button_clicked), &context);
186     gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0);
187    
188     gtk_container_add(GTK_CONTAINER(alignment), hbox);
189     gtk_box_pack_start_defaults(GTK_BOX((GTK_DIALOG(context.dialog))->vbox),
190     alignment);
191    
192     gtk_widget_show_all(alignment);
193     #endif
194    
195     gtk_dialog_run(GTK_DIALOG(context.dialog));
196     gtk_widget_destroy(context.dialog);
197 harbaum 1 }
198    
199     void on_window_destroy (GtkWidget *widget, gpointer data);
200    
201 harbaum 188 #ifndef USE_HILDON
202 harbaum 1 static void
203 harbaum 139 cb_menu_quit(GtkMenuItem *item, gpointer data) {
204 harbaum 1 appdata_t *appdata = (appdata_t*)data;
205     gtk_widget_destroy(GTK_WIDGET(appdata->window));
206     }
207 harbaum 188 #endif
208 harbaum 1
209     static void
210 harbaum 139 cb_menu_upload(GtkMenuItem *item, gpointer data) {
211 harbaum 1 appdata_t *appdata = (appdata_t*)data;
212     if(!appdata->osm || !appdata->project) return;
213    
214 harbaum 179 if(project_check_demo(GTK_WIDGET(appdata->window), appdata->project))
215 harbaum 178 return;
216    
217 harbaum 1 osm_upload(appdata, appdata->osm, appdata->project);
218     }
219    
220     static void
221 harbaum 139 cb_menu_download(GtkMenuItem *item, gpointer data) {
222 harbaum 1 appdata_t *appdata = (appdata_t*)data;
223 harbaum 4 if(!appdata->project) return;
224 harbaum 1
225 harbaum 179 if(project_check_demo(GTK_WIDGET(appdata->window), appdata->project))
226 harbaum 178 return;
227    
228 harbaum 4 /* if we have valid osm data loaded: save state first */
229     if(appdata->osm) {
230     /* redraw the entire map by destroying all map items and redrawing them */
231     diff_save(appdata->project, appdata->osm);
232     map_clear(appdata, MAP_LAYER_OBJECTS_ONLY);
233 harbaum 271
234 harbaum 4 osm_free(&appdata->icon, appdata->osm);
235     appdata->osm = NULL;
236     }
237    
238 harbaum 1 // download
239 harbaum 169 if(osm_download(GTK_WIDGET(appdata->window), appdata->settings,
240     appdata->project)) {
241 harbaum 177 banner_busy_start(appdata, 1, "Redrawing");
242 harbaum 175 appdata->osm = osm_parse(appdata->project->path, appdata->project->osm);
243 harbaum 4 diff_restore(appdata, appdata->project, appdata->osm);
244     map_paint(appdata);
245 harbaum 177 banner_busy_stop(appdata); //"Redrawing"
246 harbaum 4 }
247 harbaum 1
248 harbaum 4 main_ui_enable(appdata);
249 harbaum 1 }
250    
251     static void
252 harbaum 139 cb_menu_wms_import(GtkMenuItem *item, gpointer data) {
253 harbaum 1 appdata_t *appdata = (appdata_t*)data;
254     wms_import(appdata);
255     }
256    
257     static void
258 harbaum 139 cb_menu_wms_clear(GtkMenuItem *item, gpointer data) {
259 harbaum 1 appdata_t *appdata = (appdata_t*)data;
260     wms_remove(appdata);
261     }
262    
263     static void
264 harbaum 139 cb_menu_wms_adjust(GtkMenuItem *item, gpointer data) {
265 harbaum 1 appdata_t *appdata = (appdata_t*)data;
266     map_action_set(appdata, MAP_ACTION_BG_ADJUST);
267     }
268    
269     /* ----------- hide objects for performance reasons ----------- */
270    
271     static void
272 harbaum 139 cb_menu_map_hide_sel(GtkMenuItem *item, gpointer data) {
273 harbaum 1 appdata_t *appdata = (appdata_t*)data;
274     map_hide_selected(appdata);
275     }
276    
277     static void
278 harbaum 139 cb_menu_map_show_all(GtkMenuItem *item, gpointer data) {
279 harbaum 1 appdata_t *appdata = (appdata_t*)data;
280     map_show_all(appdata);
281     }
282    
283 harbaum 14 /* ---------------------------------------------------------- */
284 harbaum 1
285 harbaum 188 #if defined(USE_HILDON) && (MAEMO_VERSION_MAJOR == 5)
286     #define MENU_CHECK_ITEM HildonCheckButton
287     #define MENU_CHECK_ITEM_ACTIVE(a) hildon_check_button_get_active(a)
288     #else
289     #define MENU_CHECK_ITEM GtkCheckMenuItem
290     #define MENU_CHECK_ITEM_ACTIVE(a) gtk_check_menu_item_get_active(a)
291 harbaum 1 #endif
292    
293     static void
294 harbaum 188 cb_menu_map_no_icons(MENU_CHECK_ITEM *item, appdata_t *appdata) {
295 harbaum 1
296 harbaum 177 banner_busy_start(appdata, 1, "Redrawing");
297 harbaum 14 map_clear(appdata, MAP_LAYER_OBJECTS_ONLY);
298    
299 harbaum 188 appdata->settings->no_icons = MENU_CHECK_ITEM_ACTIVE(item);
300 harbaum 24
301     map_paint(appdata);
302 harbaum 177 banner_busy_stop(appdata); //"Redrawing"
303 harbaum 24 }
304    
305     static void
306 harbaum 162 cb_menu_style(GtkMenuItem *item, gpointer data) {
307     appdata_t *appdata = (appdata_t*)data;
308    
309     style_select(GTK_WIDGET(appdata->window), appdata);
310     }
311    
312     static void
313 harbaum 139 cb_menu_undo(GtkMenuItem *item, gpointer data) {
314 harbaum 64 appdata_t *appdata = (appdata_t*)data;
315    
316     undo(appdata);
317    
318     // the banner will be displayed from within undo with more details
319     }
320    
321     static void
322 harbaum 139 cb_menu_save_changes(GtkMenuItem *item, gpointer data) {
323 harbaum 14 appdata_t *appdata = (appdata_t*)data;
324    
325 harbaum 1 diff_save(appdata->project, appdata->osm);
326 achadwick 28 banner_show_info(appdata, _("Saved local changes"));
327 harbaum 1 }
328    
329 harbaum 15 static void
330 harbaum 139 cb_menu_undo_changes(GtkMenuItem *item, gpointer data) {
331 harbaum 15 appdata_t *appdata = (appdata_t*)data;
332 harbaum 1
333 harbaum 15 if(!yes_no_f(GTK_WIDGET(appdata->window), NULL, 0, 0,
334 harbaum 242 _("Undo all changes?"),
335 harbaum 69 _("Throw away all the changes you've not "
336     "uploaded yet? This can't be undone.")))
337 harbaum 15 return;
338 achadwick 28
339 harbaum 177 banner_busy_start(appdata, 1, _("Redrawing"));
340 harbaum 15 map_clear(appdata, MAP_LAYER_OBJECTS_ONLY);
341 harbaum 271
342 harbaum 15 osm_free(&appdata->icon, appdata->osm);
343 harbaum 271 appdata->osm = NULL;
344    
345 harbaum 15 diff_remove(appdata->project);
346 harbaum 175 appdata->osm = osm_parse(appdata->project->path, appdata->project->osm);
347 harbaum 15 map_paint(appdata);
348 harbaum 177 banner_busy_stop(appdata); //"Redrawing"
349 harbaum 15
350 harbaum 242 banner_show_info(appdata, _("Undo all changes"));
351 harbaum 15 }
352    
353 harbaum 1 static void
354 harbaum 191 cb_menu_osm_relations(GtkMenuItem *item, appdata_t *appdata) {
355     /* list relations of all objects */
356     relation_list(GTK_WIDGET(appdata->window), appdata, NULL);
357 harbaum 76 }
358    
359 harbaum 167 #if !defined(USE_HILDON) || (MAEMO_VERSION_MAJOR < 5)
360 harbaum 76 static void
361 harbaum 188 cb_menu_fullscreen(MENU_CHECK_ITEM *item, gpointer data) {
362 harbaum 1 appdata_t *appdata = (appdata_t *)data;
363    
364 harbaum 188 if(MENU_CHECK_ITEM_ACTIVE(item))
365 harbaum 1 gtk_window_fullscreen(GTK_WINDOW(appdata->window));
366     else
367     gtk_window_unfullscreen(GTK_WINDOW(appdata->window));
368     }
369 harbaum 167 #endif
370 harbaum 1
371     static void
372 harbaum 139 cb_menu_zoomin(GtkMenuItem *item, appdata_t *appdata) {
373 harbaum 1 if(!appdata || !appdata->map) return;
374    
375     map_set_zoom(appdata->map, appdata->map->state->zoom*ZOOM_FACTOR_MENU, TRUE);
376     printf("zoom is now %f\n", appdata->map->state->zoom);
377     }
378    
379     static void
380 harbaum 139 cb_menu_zoomout(GtkMenuItem *item, appdata_t *appdata) {
381 harbaum 1 if(!appdata || !appdata->map) return;
382    
383     map_set_zoom(appdata->map, appdata->map->state->zoom/ZOOM_FACTOR_MENU, TRUE);
384     printf("zoom is now %f\n", appdata->map->state->zoom);
385     }
386    
387 harbaum 249 #if (MAEMO_VERSION_MAJOR != 5) || !defined(DETAIL_POPUP)
388 harbaum 1 static void
389 harbaum 162 cb_menu_view_detail_inc(GtkMenuItem *item, gpointer data) {
390     appdata_t *appdata = (appdata_t*)data;
391    
392     printf("detail level increase\n");
393     map_detail_increase(appdata->map);
394     }
395    
396     static void
397     cb_menu_view_detail_normal(GtkMenuItem *item, gpointer data) {
398     appdata_t *appdata = (appdata_t*)data;
399    
400     printf("detail level normal\n");
401     map_detail_normal(appdata->map);
402     }
403    
404     static void
405     cb_menu_view_detail_dec(GtkMenuItem *item, gpointer data) {
406     appdata_t *appdata = (appdata_t*)data;
407    
408     printf("detail level decrease\n");
409     map_detail_decrease(appdata->map);
410     }
411 harbaum 249 #endif
412 harbaum 162
413     static void
414 harbaum 139 cb_menu_track_import(GtkMenuItem *item, appdata_t *appdata) {
415 harbaum 156 g_assert(appdata->settings);
416 harbaum 1
417     /* open a file selector */
418     GtkWidget *dialog;
419    
420     #ifdef USE_HILDON
421     dialog = hildon_file_chooser_dialog_new(GTK_WINDOW(appdata->window),
422     GTK_FILE_CHOOSER_ACTION_OPEN);
423     #else
424     dialog = gtk_file_chooser_dialog_new (_("Import track file"),
425     GTK_WINDOW(appdata->window),
426     GTK_FILE_CHOOSER_ACTION_OPEN,
427     GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
428     GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT,
429     NULL);
430     #endif
431    
432 harbaum 156 if(appdata->settings->track_path) {
433     if(!g_file_test(appdata->settings->track_path, G_FILE_TEST_EXISTS)) {
434     char *last_sep = strrchr(appdata->settings->track_path, '/');
435     if(last_sep) {
436     *last_sep = 0; // seperate path from file
437    
438     /* the user just created a new document */
439     gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog),
440     appdata->settings->track_path);
441     gtk_file_chooser_set_current_name(GTK_FILE_CHOOSER(dialog),
442     last_sep+1);
443    
444     /* restore full filename */
445     *last_sep = '/';
446     }
447     } else
448     gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(dialog),
449     appdata->settings->track_path);
450     }
451    
452 harbaum 1 gtk_widget_show_all (GTK_WIDGET(dialog));
453     if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_FM_OK) {
454     char *filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dialog));
455    
456     /* load a track */
457 harbaum 156 appdata->track.track = track_import(appdata, filename);
458 harbaum 1 if(appdata->track.track) {
459 harbaum 156 if(appdata->settings->track_path) g_free(appdata->settings->track_path);
460     appdata->settings->track_path = g_strdup(filename);
461 harbaum 1 }
462     g_free (filename);
463     }
464    
465     gtk_widget_destroy (dialog);
466     }
467    
468     static void
469 harbaum 188 cb_menu_track_enable_gps(MENU_CHECK_ITEM *item, appdata_t *appdata) {
470     track_enable_gps(appdata, MENU_CHECK_ITEM_ACTIVE(item));
471 harbaum 1 }
472    
473 harbaum 156
474 harbaum 1 static void
475 harbaum 188 cb_menu_track_follow_gps(MENU_CHECK_ITEM *item, appdata_t *appdata) {
476     appdata->settings->follow_gps = MENU_CHECK_ITEM_ACTIVE(item);
477 harbaum 1 }
478    
479 harbaum 156
480 harbaum 1 static void
481 harbaum 156 cb_menu_track_export(GtkMenuItem *item, appdata_t *appdata) {
482     g_assert(appdata->settings);
483    
484     /* open a file selector */
485     GtkWidget *dialog;
486    
487     #ifdef USE_HILDON
488     dialog = hildon_file_chooser_dialog_new(GTK_WINDOW(appdata->window),
489     GTK_FILE_CHOOSER_ACTION_SAVE);
490     #else
491     dialog = gtk_file_chooser_dialog_new(_("Export track file"),
492     GTK_WINDOW(appdata->window),
493     GTK_FILE_CHOOSER_ACTION_SAVE,
494     GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
495     GTK_STOCK_SAVE, GTK_RESPONSE_ACCEPT,
496     NULL);
497     #endif
498    
499     printf("set filename <%s>\n", appdata->settings->track_path);
500    
501     if(appdata->settings->track_path) {
502     if(!g_file_test(appdata->settings->track_path, G_FILE_TEST_EXISTS)) {
503     char *last_sep = strrchr(appdata->settings->track_path, '/');
504     if(last_sep) {
505     *last_sep = 0; // seperate path from file
506    
507     /* the user just created a new document */
508     gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(dialog),
509     appdata->settings->track_path);
510     gtk_file_chooser_set_current_name(GTK_FILE_CHOOSER(dialog),
511     last_sep+1);
512    
513     /* restore full filename */
514     *last_sep = '/';
515     }
516     } else
517     gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(dialog),
518     appdata->settings->track_path);
519     }
520    
521     if(gtk_dialog_run(GTK_DIALOG(dialog)) == GTK_FM_OK) {
522     gchar *filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dialog));
523     if(filename) {
524     printf("export to %s\n", filename);
525    
526     if(!g_file_test(filename, G_FILE_TEST_EXISTS) ||
527     yes_no_f(dialog, appdata, MISC_AGAIN_ID_EXPORT_OVERWRITE,
528     MISC_AGAIN_FLAG_DONT_SAVE_NO,
529     "Overwrite existing file",
530     "The file already exists. "
531     "Do you really want to replace it?")) {
532     if(appdata->settings->track_path)
533     g_free(appdata->settings->track_path);
534     appdata->settings->track_path = g_strdup(filename);
535    
536     track_export(appdata, filename);
537     }
538     }
539     }
540    
541     gtk_widget_destroy (dialog);
542     }
543    
544    
545     static void
546 harbaum 139 cb_menu_track_clear(GtkMenuItem *item, gpointer data) {
547 harbaum 1 appdata_t *appdata = (appdata_t*)data;
548 harbaum 156 track_clear(appdata, appdata->track.track);
549     appdata->track.track = NULL;
550 harbaum 1 }
551    
552 achadwick 55
553    
554    
555     /*
556     * Platform-specific UI tweaks.
557     */
558    
559    
560 achadwick 37 #ifndef USE_HILDON
561     #ifdef PORTRAIT
562 achadwick 55
563     // Portrait mode, for openmoko-like systems
564     #define uispecific_main_menu_new gtk_menu_new
565    
566 achadwick 37 #else
567 achadwick 55
568     // Regular desktop builds
569     #define uispecific_main_menu_new gtk_menu_bar_new
570     #define UISPECIFIC_MAIN_MENU_IS_MENU_BAR
571     #define UISPECIFIC_MENU_HAS_ICONS
572     #define UISPECIFIC_MENU_HAS_ACCELS
573    
574 achadwick 37 #endif //PORTRAIT
575 achadwick 55 #else//USE_HILDON
576    
577     // Maemo/Hildon builds
578     #define uispecific_main_menu_new gtk_menu_new
579    
580 achadwick 37 #endif
581    
582 achadwick 55
583 harbaum 188 #if !defined(USE_HILDON) || (MAEMO_VERSION_MAJOR < 5)
584 achadwick 55 // Half-arsed slapdash common menu item constructor. Let's use GtkBuilder
585     // instead so we have some flexibility.
586    
587     static GtkWidget *
588     menu_append_new_item(appdata_t *appdata,
589     GtkWidget *menu_shell,
590     GtkSignalFunc activate_cb,
591     char *label,
592 achadwick 79 const gchar *icon_name, // stock id or name for icon_load
593     // overridden by label, accels, icon_name
594 achadwick 55 const gchar *accel_path,
595     guint accel_key, // from gdk/gdkkeysyms.h
596     GdkModifierType accel_mods, // e.g. GDK_CONTROL_MASK
597 harbaum 156 gboolean enabled,
598 achadwick 55 gboolean is_check, gboolean check_status)
599     {
600     GtkWidget *item = NULL;
601 achadwick 79 GtkWidget *image = NULL;
602    
603     gboolean stock_item_known = FALSE;
604 achadwick 55 GtkStockItem stock_item;
605 achadwick 79 if (icon_name != NULL) {
606     stock_item_known = gtk_stock_lookup(icon_name, &stock_item);
607 achadwick 55 }
608    
609     // Icons
610     #ifndef UISPECIFIC_MENU_HAS_ICONS
611     item = is_check ? gtk_check_menu_item_new_with_mnemonic (label)
612     : gtk_menu_item_new_with_mnemonic (label);
613     #else
614 achadwick 79 if (is_check) {
615     item = gtk_check_menu_item_new_with_mnemonic (label);
616 achadwick 55 }
617 achadwick 79 else if (!stock_item_known) {
618     GdkPixbuf *pbuf = icon_load(&appdata->icon, icon_name);
619     if (pbuf) {
620     image = gtk_image_new_from_pixbuf(pbuf);
621     }
622     if (image) {
623     item = gtk_image_menu_item_new_with_mnemonic(label);
624     gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(item), image);
625     }
626     else {
627     item = gtk_menu_item_new_with_mnemonic(label);
628     }
629     }
630 achadwick 55 else {
631     item = gtk_image_menu_item_new_with_mnemonic(label);
632 achadwick 79 image = gtk_image_new_from_stock(icon_name, GTK_ICON_SIZE_MENU);
633     gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(item), image);
634 achadwick 55 }
635     #endif
636    
637     #ifdef UISPECIFIC_MENU_HAS_ACCELS
638     // Accelerators
639     // Default
640     if (accel_path != NULL) {
641     gtk_menu_item_set_accel_path(GTK_MENU_ITEM(item), accel_path);
642     if (accel_key != 0) {
643     gtk_accel_map_add_entry( accel_path, accel_key, accel_mods );
644     }
645     else if (stock_item_known) {
646     gtk_accel_map_add_entry( accel_path, stock_item.keyval,
647     stock_item.modifier );
648     }
649     }
650     #endif
651    
652     gtk_menu_shell_append(GTK_MENU_SHELL(menu_shell), GTK_WIDGET(item));
653 harbaum 156 gtk_widget_set_sensitive(GTK_WIDGET(item), enabled);
654     if (is_check)
655 achadwick 55 gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(item), check_status);
656 harbaum 156
657 achadwick 55 g_signal_connect(item, "activate", GTK_SIGNAL_FUNC(activate_cb),
658     appdata);
659     return item;
660     }
661    
662 harbaum 1 void menu_create(appdata_t *appdata) {
663     GtkWidget *menu, *item, *submenu;
664 achadwick 37 GtkWidget *about_quit_items_menu;
665 achadwick 55
666     if (g_module_supported()) {
667     printf("*** can use GModule: consider using GtkUIManager / GtkBuilder\n");
668     }
669    
670     menu = uispecific_main_menu_new();
671 achadwick 37 about_quit_items_menu = menu;
672 harbaum 1
673     /* -------------------- Project submenu -------------------- */
674    
675 achadwick 55 GtkAccelGroup *accel_grp = gtk_accel_group_new();
676 harbaum 232
677     #ifndef USE_HILDON
678 achadwick 55 item = gtk_menu_item_new_with_mnemonic( _("_Project") );
679 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
680 harbaum 1 submenu = gtk_menu_new();
681 achadwick 55 gtk_menu_set_accel_group(GTK_MENU(submenu), accel_grp);
682 harbaum 1 gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), submenu);
683 achadwick 55 #ifdef UISPECIFIC_MAIN_MENU_IS_MENU_BAR
684 achadwick 37 about_quit_items_menu = submenu;
685     #endif
686 harbaum 1
687 achadwick 55 menu_append_new_item(
688 harbaum 177 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_project_open), _("_Open"),
689 achadwick 55 GTK_STOCK_OPEN, "<OSM2Go-Main>/Project/Open",
690 harbaum 156 0, 0, TRUE, FALSE, FALSE
691 achadwick 55 );
692 harbaum 1
693 harbaum 185 menu_append_new_item(
694     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_project_wizard), _("_Wizard"),
695     GTK_STOCK_NEW, "<OSM2Go-Main>/Project/Wizard",
696 harbaum 156 0, 0, TRUE, FALSE, FALSE
697 achadwick 55 );
698 harbaum 232 #else
699     menu_append_new_item(
700     appdata, menu, GTK_SIGNAL_FUNC(cb_menu_project_open), _("_Project"),
701     GTK_STOCK_OPEN, "<OSM2Go-Main>/Project",
702     0, 0, TRUE, FALSE, FALSE
703     );
704 harbaum 207 #endif
705 harbaum 1
706     /* --------------- view menu ------------------- */
707    
708 achadwick 79 #ifndef UISPECIFIC_MAIN_MENU_IS_MENU_BAR
709 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(menu), gtk_separator_menu_item_new());
710     #endif
711 harbaum 1
712 harbaum 189 appdata->submenu_view = item = gtk_menu_item_new_with_mnemonic( _("_View") );
713 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
714 harbaum 1 submenu = gtk_menu_new();
715 achadwick 55 gtk_menu_set_accel_group(GTK_MENU(submenu), accel_grp);
716 harbaum 1 gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), submenu);
717    
718 harbaum 167 #if !defined(USE_HILDON) || (MAEMO_VERSION_MAJOR < 5)
719 achadwick 55 appdata->menu_item_view_fullscreen = menu_append_new_item(
720     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_fullscreen), _("_Fullscreen"),
721     GTK_STOCK_FULLSCREEN, "<OSM2Go-Main>/View/Fullscreen",
722 harbaum 156 0, 0, TRUE, TRUE, FALSE
723 achadwick 55 );
724 harbaum 167 #endif
725 harbaum 1
726 harbaum 231 #if !defined(ZOOM_BUTTONS) || !defined(USE_HILDON)
727 achadwick 55 menu_append_new_item(
728     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_zoomin), _("Zoom _in"),
729     GTK_STOCK_ZOOM_IN, "<OSM2Go-Main>/View/ZoomIn",
730 harbaum 156 GDK_comma, GDK_CONTROL_MASK, TRUE, FALSE, FALSE
731 achadwick 55 );
732 harbaum 1
733 achadwick 55 menu_append_new_item(
734     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_zoomout), _("Zoom _out"),
735     GTK_STOCK_ZOOM_OUT, "<OSM2Go-Main>/View/ZoomOut",
736 harbaum 156 GDK_period, GDK_CONTROL_MASK, TRUE, FALSE, FALSE
737 achadwick 55 );
738 harbaum 231 #endif
739 harbaum 1
740 harbaum 162 gtk_menu_shell_append(GTK_MENU_SHELL(submenu), gtk_separator_menu_item_new());
741    
742     menu_append_new_item(
743     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_view_detail_inc), _("More details"),
744     NULL, "<OSM2Go-Main>/View/DetailInc",
745     GDK_period, GDK_MOD1_MASK, TRUE, FALSE, FALSE
746     );
747    
748     menu_append_new_item(
749     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_view_detail_normal), _("Normal details"),
750     NULL, "<OSM2Go-Main>/View/DetailNormal",
751     0, 0, TRUE, FALSE, FALSE
752     );
753    
754     menu_append_new_item(
755     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_view_detail_dec), _("Less details"),
756     NULL, "<OSM2Go-Main>/View/DetailDec",
757     GDK_comma, GDK_MOD1_MASK, TRUE, FALSE, FALSE
758     );
759    
760 harbaum 188 gtk_menu_shell_append(GTK_MENU_SHELL(submenu), gtk_separator_menu_item_new());
761 harbaum 1
762 harbaum 188 appdata->menu_item_map_hide_sel = menu_append_new_item(
763     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_map_hide_sel), _("_Hide selected"),
764 harbaum 189 GTK_STOCK_REMOVE, "<OSM2Go-Main>/View/HideSelected",
765 harbaum 188 0, 0, TRUE, FALSE, FALSE
766     );
767     gtk_widget_set_sensitive(appdata->menu_item_map_hide_sel, FALSE);
768    
769     appdata->menu_item_map_show_all = menu_append_new_item(
770     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_map_show_all), _("_Show all"),
771 harbaum 189 GTK_STOCK_ADD, "<OSM2Go-Main>/View/ShowAll",
772 harbaum 188 0, 0, TRUE, FALSE, FALSE
773     );
774     gtk_widget_set_sensitive(appdata->menu_item_map_show_all, FALSE);
775    
776     gtk_menu_shell_append(GTK_MENU_SHELL(submenu), gtk_separator_menu_item_new());
777    
778     menu_append_new_item(
779     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_style), _("St_yle"),
780 harbaum 189 GTK_STOCK_SELECT_COLOR, "<OSM2Go-Main>/View/Style",
781 harbaum 188 0, 0, TRUE, FALSE, FALSE
782     );
783    
784     gtk_menu_shell_append(GTK_MENU_SHELL(submenu), gtk_separator_menu_item_new());
785    
786     appdata->menu_item_map_no_icons = menu_append_new_item(
787     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_map_no_icons), _("No _icons"),
788 harbaum 189 NULL, "<OSM2Go-Main>/View/NoIcons",
789 harbaum 188 0, 0, TRUE, TRUE, appdata->settings->no_icons
790     );
791    
792    
793     /* -------------------- map submenu -------------------- */
794    
795 harbaum 189 appdata->submenu_map = item = gtk_menu_item_new_with_mnemonic( _("_Map") );
796 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
797 harbaum 1 submenu = gtk_menu_new();
798 achadwick 55 gtk_menu_set_accel_group(GTK_MENU(submenu), accel_grp);
799 harbaum 1 gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), submenu);
800 harbaum 188
801 harbaum 189 appdata->menu_item_map_upload = menu_append_new_item(
802 harbaum 177 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_upload), _("_Upload"),
803 harbaum 189 "upload.16", "<OSM2Go-Main>/Map/Upload",
804 harbaum 156 GDK_u, GDK_SHIFT_MASK|GDK_CONTROL_MASK, TRUE, FALSE, FALSE
805 achadwick 55 );
806 harbaum 1
807 achadwick 55 menu_append_new_item(
808 harbaum 177 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_download), _("_Download"),
809 harbaum 189 "download.16", "<OSM2Go-Main>/Map/Download",
810 harbaum 156 GDK_d, GDK_SHIFT_MASK|GDK_CONTROL_MASK, TRUE, FALSE, FALSE
811 achadwick 55 );
812 harbaum 1
813 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(submenu), gtk_separator_menu_item_new());
814 harbaum 1
815 harbaum 64 if(getenv("OSM2GO_UNDO_TEST")) {
816 harbaum 189 appdata->menu_item_map_undo = menu_append_new_item(
817 harbaum 64 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_undo), _("_Undo"),
818 harbaum 189 GTK_STOCK_UNDO, "<OSM2Go-Main>/Map/Undo",
819 harbaum 156 GDK_z, GDK_CONTROL_MASK, TRUE, FALSE, FALSE
820 harbaum 64 );
821     } else
822     printf("set environment variable OSM2GO_UNDO_TEST to enable undo framework tests\n");
823 harbaum 1
824 harbaum 244 #ifndef USE_HILDON
825 harbaum 189 appdata->menu_item_map_save_changes = menu_append_new_item(
826 achadwick 55 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_save_changes), _("_Save local changes"),
827 harbaum 189 GTK_STOCK_SAVE, "<OSM2Go-Main>/Map/SaveChanges",
828 harbaum 156 GDK_s, GDK_SHIFT_MASK|GDK_CONTROL_MASK, TRUE, FALSE, FALSE
829 achadwick 55 );
830 harbaum 244 #endif
831 harbaum 15
832 harbaum 189 appdata->menu_item_map_undo_changes = menu_append_new_item(
833 harbaum 242 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_undo_changes), _("Undo _all"),
834     GTK_STOCK_DELETE, "<OSM2Go-Main>/Map/UndoAll",
835 harbaum 156 0, 0, TRUE, FALSE, FALSE
836 achadwick 55 );
837    
838 harbaum 76 gtk_menu_shell_append(GTK_MENU_SHELL(submenu), gtk_separator_menu_item_new());
839 harbaum 189 appdata->menu_item_map_relations = menu_append_new_item(
840 harbaum 177 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_osm_relations), _("_Relations"),
841 harbaum 189 NULL, "<OSM2Go-Main>/Map/Relations",
842 harbaum 156 GDK_r, GDK_SHIFT_MASK|GDK_CONTROL_MASK, TRUE, FALSE, FALSE
843 harbaum 76 );
844    
845 harbaum 1 /* -------------------- wms submenu -------------------- */
846    
847 harbaum 189 appdata->submenu_wms = item = gtk_menu_item_new_with_mnemonic( _("_WMS") );
848 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
849 harbaum 1 submenu = gtk_menu_new();
850 achadwick 55 gtk_menu_set_accel_group(GTK_MENU(submenu), accel_grp);
851 harbaum 1 gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), submenu);
852    
853 achadwick 55 menu_append_new_item(
854 harbaum 177 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_wms_import), _("_Import"),
855 achadwick 55 GTK_STOCK_INDEX, "<OSM2Go-Main>/WMS/Import",
856 harbaum 156 0, 0, TRUE, FALSE, FALSE
857 achadwick 55 );
858 harbaum 1
859 achadwick 55 appdata->menu_item_wms_clear = menu_append_new_item(
860     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_wms_clear), _("_Clear"),
861     GTK_STOCK_CLEAR, "<OSM2Go-Main>/WMS/Clear",
862 harbaum 156 0, 0, TRUE, FALSE, FALSE
863 achadwick 55 );
864     gtk_widget_set_sensitive(appdata->menu_item_wms_clear, FALSE);
865 harbaum 1
866 achadwick 55 appdata->menu_item_wms_adjust = menu_append_new_item(
867     appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_wms_adjust), _("_Adjust"),
868     NULL, "<OSM2Go-Main>/WMS/Adjust",
869 harbaum 156 0, 0, TRUE, FALSE, FALSE
870 achadwick 55 );
871     gtk_widget_set_sensitive(appdata->menu_item_wms_adjust, FALSE);
872 harbaum 1
873     /* -------------------- track submenu -------------------- */
874    
875 harbaum 189 appdata->track.submenu_track = item =
876     gtk_menu_item_new_with_mnemonic(_("_Track"));
877 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
878 harbaum 1 submenu = gtk_menu_new();
879 achadwick 55 gtk_menu_set_accel_group(GTK_MENU(submenu), accel_grp);
880 harbaum 1 gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), submenu);
881    
882 harbaum 189 appdata->track.menu_item_track_import = menu_append_new_item(
883 harbaum 177 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_track_import), _("_Import"),
884 achadwick 55 NULL, "<OSM2Go-Main>/Track/Import",
885 harbaum 156 0, 0, TRUE, FALSE, FALSE
886 achadwick 55 );
887 harbaum 1
888 harbaum 189 appdata->track.menu_item_track_export = menu_append_new_item(
889 harbaum 177 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_track_export), _("_Export"),
890 achadwick 55 NULL, "<OSM2Go-Main>/Track/Export",
891 harbaum 156 0, 0, FALSE, FALSE, FALSE
892 achadwick 55 );
893 harbaum 1
894 harbaum 189 appdata->track.menu_item_track_clear = menu_append_new_item(
895 achadwick 55 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_track_clear), _("_Clear"),
896     GTK_STOCK_CLEAR, "<OSM2Go-Main>/Track/Clear",
897 harbaum 156 0, 0, FALSE, FALSE, FALSE
898 achadwick 55 );
899 harbaum 1
900 achadwick 55
901 harbaum 189 appdata->track.menu_item_track_enable_gps = menu_append_new_item(
902 harbaum 156 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_track_enable_gps),_("_GPS enable"),
903 achadwick 55 NULL, "<OSM2Go-Main>/Track/GPS",
904 harbaum 156 GDK_g, GDK_CONTROL_MASK|GDK_SHIFT_MASK, TRUE, TRUE,
905     appdata->settings->enable_gps
906 achadwick 55 );
907 harbaum 156
908 harbaum 189 appdata->track.menu_item_track_follow_gps = menu_append_new_item(
909 harbaum 156 appdata, submenu, GTK_SIGNAL_FUNC(cb_menu_track_follow_gps), _("GPS follow"),
910     NULL, "<OSM2Go-Main>/Track/Follow",
911     0, 0, appdata->settings->enable_gps, TRUE,
912     appdata->settings->follow_gps
913     );
914 harbaum 1
915     /* ------------------------------------------------------- */
916    
917 achadwick 37 gtk_menu_shell_append(GTK_MENU_SHELL(about_quit_items_menu),
918     gtk_separator_menu_item_new());
919 harbaum 1
920 achadwick 55 menu_append_new_item(
921 harbaum 177 appdata, about_quit_items_menu, GTK_SIGNAL_FUNC(cb_menu_about), _("_About"),
922 achadwick 55 GTK_STOCK_ABOUT, "<OSM2Go-Main>/About",
923 harbaum 156 0, 0, TRUE, FALSE, FALSE
924 achadwick 55 );
925 harbaum 1
926 harbaum 188 #ifndef USE_HILDON
927 achadwick 55 menu_append_new_item(
928     appdata, about_quit_items_menu, GTK_SIGNAL_FUNC(cb_menu_quit), _("_Quit"),
929     GTK_STOCK_QUIT, "<OSM2Go-Main>/Quit",
930 harbaum 156 0, 0, TRUE, FALSE, FALSE
931 achadwick 55 );
932 harbaum 188 #endif
933 harbaum 1
934 achadwick 55 gtk_window_add_accel_group(GTK_WINDOW(appdata->window), accel_grp);
935    
936 harbaum 1 #ifdef USE_HILDON
937     hildon_window_set_menu(appdata->window, GTK_MENU(menu));
938     #else
939 achadwick 37 GtkWidget *menu_bar = menu;
940 harbaum 1
941 achadwick 55 #ifndef UISPECIFIC_MAIN_MENU_IS_MENU_BAR
942 achadwick 37 // we need to make one first
943     menu_bar = gtk_menu_bar_new();
944    
945 harbaum 1 GtkWidget *root_menu = gtk_menu_item_new_with_label (_("Menu"));
946     gtk_widget_show(root_menu);
947    
948     gtk_menu_bar_append(menu_bar, root_menu);
949     gtk_menu_item_set_submenu(GTK_MENU_ITEM (root_menu), menu);
950    
951     gtk_widget_show(menu_bar);
952 achadwick 55 #endif //UISPECIFIC_MAIN_MENU_IS_MENU_BAR
953 achadwick 37
954 harbaum 1 gtk_box_pack_start(GTK_BOX(appdata->vbox), menu_bar, 0, 0, 0);
955 achadwick 37
956     #endif //USE_HILDON
957 harbaum 1 }
958 harbaum 245
959     void menu_cleanup(appdata_t *appdata) { }
960    
961 harbaum 188 #else // !defined(USE_HILDON) || (MAEMO_VERSION_MAJOR < 5)
962 harbaum 1
963 harbaum 188 void submenu_entry(appdata_t *appdata, HildonAppMenu *menu,
964     const char *label, const char *value,
965     GtkSignalFunc activate_cb) {
966    
967     }
968    
969     typedef struct {
970     const char *label, *value;
971     gboolean enabled;
972     gboolean (*toggle)(appdata_t *appdata);
973     gulong offset;
974     GtkSignalFunc activate_cb;
975     } menu_entry_t;
976    
977 harbaum 242 typedef struct {
978     const char *title;
979     const menu_entry_t *menu;
980     int len;
981     } submenu_t;
982    
983 harbaum 188 static gboolean no_icon_get_toggle(appdata_t *appdata) {
984     if(!appdata) return FALSE;
985     if(!appdata->settings) return FALSE;
986     return appdata->settings->no_icons;
987     }
988    
989 harbaum 190 static gboolean enable_gps_get_toggle(appdata_t *appdata) {
990     if(!appdata) return FALSE;
991 harbaum 192 if(!appdata->settings) return FALSE;
992     return appdata->settings->enable_gps;
993 harbaum 190 }
994    
995     static gboolean follow_gps_get_toggle(appdata_t *appdata) {
996     if(!appdata) return FALSE;
997     if(!appdata->settings) return FALSE;
998     return appdata->settings->follow_gps;
999     }
1000    
1001 harbaum 188 /* create a HildonAppMenu */
1002 harbaum 190 static GtkWidget *app_menu_create(appdata_t *appdata,
1003     const menu_entry_t *menu_entries) {
1004 harbaum 188 HildonAppMenu *menu = HILDON_APP_MENU(hildon_app_menu_new());
1005    
1006     while(menu_entries->label) {
1007     GtkWidget *button = NULL;
1008    
1009     if(!menu_entries->toggle) {
1010     button = hildon_button_new_with_text(
1011     HILDON_SIZE_FINGER_HEIGHT | HILDON_SIZE_AUTO_WIDTH,
1012     HILDON_BUTTON_ARRANGEMENT_VERTICAL,
1013 harbaum 190 _(menu_entries->label), _(menu_entries->value));
1014     g_signal_connect_after(button, "clicked",
1015     menu_entries->activate_cb, appdata);
1016 harbaum 188 } else {
1017     button = hildon_check_button_new(HILDON_SIZE_AUTO);
1018     gtk_button_set_label(GTK_BUTTON(button), _(menu_entries->label));
1019 harbaum 192 printf("requesting check for %s: %p\n", menu_entries->label,
1020     menu_entries->toggle);
1021 harbaum 188 hildon_check_button_set_active(HILDON_CHECK_BUTTON(button),
1022     menu_entries->toggle(appdata));
1023 harbaum 190 g_signal_connect_after(button, "toggled",
1024     menu_entries->activate_cb, appdata);
1025 harbaum 188 }
1026    
1027 harbaum 245 hildon_button_set_title_alignment(HILDON_BUTTON(button), 0.5, 0.5);
1028     hildon_button_set_value_alignment(HILDON_BUTTON(button), 0.5, 0.5);
1029    
1030 harbaum 188 /* offset to GtkWidget pointer was given -> store pointer */
1031     if(menu_entries->offset)
1032     *(GtkWidget**)(((void*)appdata)+menu_entries->offset) = button;
1033    
1034     gtk_widget_set_sensitive(button, menu_entries->enabled);
1035    
1036     hildon_app_menu_append(menu, GTK_BUTTON(button));
1037     menu_entries++;
1038     }
1039    
1040     gtk_widget_show_all(GTK_WIDGET(menu));
1041     return GTK_WIDGET(menu);
1042     }
1043    
1044 harbaum 242 #ifdef MAEMO5_SUBMENU_POPUP
1045     static GtkWidget *app_submenu_create(appdata_t *appdata,
1046     const submenu_t *submenu) {
1047     return app_menu_create(appdata, submenu->menu);
1048     }
1049    
1050 harbaum 228 static void submenu_popup(GtkWidget *menu) {
1051     GtkWidget *top = hildon_window_stack_peek(hildon_window_stack_get_default());
1052    
1053 harbaum 242 #if 0 // nasty workaround for race condition in hildonappmenu
1054 harbaum 228 int start, end;
1055     GTimeVal tv;
1056     g_get_current_time(&tv);
1057     start = tv.tv_sec * 1000 + tv.tv_usec / 1000;
1058     do {
1059     if(gtk_events_pending())
1060     while(gtk_events_pending()) {
1061     putchar('.'); fflush(stdout);
1062     gtk_main_iteration();
1063     }
1064     else
1065     usleep(100);
1066    
1067     g_get_current_time(&tv);
1068     end = tv.tv_sec * 1000 + tv.tv_usec / 1000;
1069     } while(end-start < 500);
1070     #endif
1071    
1072 harbaum 242 hildon_app_menu_popup(HILDON_APP_MENU(menu), GTK_WINDOW(top));
1073     }
1074    
1075     static void submenu_cleanup(GtkWidget *menu) {
1076     g_object_unref(menu);
1077     }
1078     #else
1079     #define COLUMNS 2
1080    
1081     void on_submenu_entry_clicked(GtkButton *button, GtkWidget *menu) {
1082    
1083     /* force closing of submenu dialog */
1084     gtk_dialog_response(GTK_DIALOG(menu), GTK_RESPONSE_NONE);
1085     gtk_widget_hide(menu);
1086 harbaum 228
1087 harbaum 242 /* let gtk clean up */
1088     while(gtk_events_pending())
1089     gtk_main_iteration();
1090     }
1091 harbaum 228
1092 harbaum 242 /* use standard dialog boxes for fremantle submenues */
1093     static GtkWidget *app_submenu_create(appdata_t *appdata,
1094     const submenu_t *submenu) {
1095    
1096     /* create a oridinary dialog box */
1097     GtkWidget *dialog = misc_dialog_new(MISC_DIALOG_SMALL, _(submenu->title),
1098     GTK_WINDOW(appdata->window), NULL);
1099    
1100     gtk_dialog_set_has_separator(GTK_DIALOG(dialog), FALSE);
1101    
1102     GtkWidget *table = gtk_table_new(submenu->len/COLUMNS, COLUMNS, TRUE);
1103     int x = 0, y = 0;
1104    
1105     const menu_entry_t *menu_entries = submenu->menu;
1106     while(menu_entries->label) {
1107     GtkWidget *button = NULL;
1108    
1109     if(!menu_entries->toggle) {
1110     button = hildon_button_new_with_text(
1111     HILDON_SIZE_FINGER_HEIGHT | HILDON_SIZE_AUTO_WIDTH,
1112     HILDON_BUTTON_ARRANGEMENT_VERTICAL,
1113     _(menu_entries->label), _(menu_entries->value));
1114    
1115     g_signal_connect(button, "clicked",
1116     G_CALLBACK(on_submenu_entry_clicked), dialog);
1117    
1118     g_signal_connect(button, "clicked",
1119     menu_entries->activate_cb, appdata);
1120 harbaum 245
1121     hildon_button_set_title_alignment(HILDON_BUTTON(button), 0.5, 0.5);
1122     hildon_button_set_value_alignment(HILDON_BUTTON(button), 0.5, 0.5);
1123 harbaum 242 } else {
1124     button = hildon_check_button_new(HILDON_SIZE_AUTO);
1125     gtk_button_set_label(GTK_BUTTON(button), _(menu_entries->label));
1126     printf("requesting check for %s: %p\n", menu_entries->label,
1127     menu_entries->toggle);
1128     hildon_check_button_set_active(HILDON_CHECK_BUTTON(button),
1129     menu_entries->toggle(appdata));
1130    
1131     g_signal_connect(button, "clicked",
1132     G_CALLBACK(on_submenu_entry_clicked), dialog);
1133    
1134     g_signal_connect(button, "toggled",
1135     menu_entries->activate_cb, appdata);
1136 harbaum 245
1137     gtk_button_set_alignment(GTK_BUTTON(button), 0.5, 0.5);
1138 harbaum 242 }
1139    
1140     /* offset to GtkWidget pointer was given -> store pointer */
1141     if(menu_entries->offset)
1142     *(GtkWidget**)(((void*)appdata)+menu_entries->offset) = button;
1143    
1144     gtk_widget_set_sensitive(button, menu_entries->enabled);
1145    
1146     gtk_table_attach_defaults(GTK_TABLE(table), button, x, x+1, y, y+1);
1147    
1148     x++;
1149     if(x == COLUMNS) { x = 0; y++; }
1150    
1151     menu_entries++;
1152     }
1153    
1154    
1155     gtk_box_pack_start_defaults(GTK_BOX(GTK_DIALOG(dialog)->vbox), table);
1156    
1157     return dialog;
1158 harbaum 228 }
1159    
1160 harbaum 242 /* popup the dialog shaped submenu */
1161     static void submenu_popup(GtkWidget *menu) {
1162     gtk_widget_show_all(menu);
1163     gtk_dialog_run(GTK_DIALOG(menu));
1164     gtk_widget_hide(menu);
1165     }
1166    
1167     static void submenu_cleanup(GtkWidget *menu) {
1168     gtk_widget_destroy(menu);
1169     }
1170     #endif
1171    
1172 harbaum 188 /* the view submenu */
1173     void on_submenu_view_clicked(GtkButton *button, appdata_t *appdata) {
1174 harbaum 228 submenu_popup(appdata->app_menu_view);
1175 harbaum 188 }
1176    
1177 harbaum 191 void on_submenu_map_clicked(GtkButton *button, appdata_t *appdata) {
1178 harbaum 228 submenu_popup(appdata->app_menu_map);
1179 harbaum 191 }
1180    
1181 harbaum 188 void on_submenu_wms_clicked(GtkButton *button, appdata_t *appdata) {
1182 harbaum 228 submenu_popup(appdata->app_menu_wms);
1183 harbaum 188 }
1184    
1185 harbaum 190 void on_submenu_track_clicked(GtkButton *button, appdata_t *appdata) {
1186 harbaum 228 submenu_popup(appdata->app_menu_track);
1187 harbaum 190 }
1188    
1189 harbaum 188 #define APP_OFFSET(a) offsetof(appdata_t, a)
1190     #define SIMPLE_ENTRY(a,b) { a, NULL, TRUE, NULL, 0, G_CALLBACK(b) }
1191 harbaum 191 #define ENABLED_ENTRY(a,b,c) { a, NULL, TRUE, NULL, APP_OFFSET(c), G_CALLBACK(b) }
1192 harbaum 188 #define DISABLED_ENTRY(a,b,c) { a, NULL, FALSE, NULL, APP_OFFSET(c), G_CALLBACK(b) }
1193 harbaum 191 #define TOGGLE_ENTRY(a,b,c) { a, NULL, TRUE, c, 0, G_CALLBACK(b) }
1194     #define DISABLED_TOGGLE_ENTRY(a,b,c,d) \
1195     { a, NULL, FALSE, c, APP_OFFSET(d), G_CALLBACK(b) }
1196     #define ENABLED_TOGGLE_ENTRY(a,b,c,d) \
1197     { a, NULL, TRUE, c, APP_OFFSET(d), G_CALLBACK(b) }
1198 harbaum 188 #define LAST_ENTRY { NULL, NULL, FALSE, NULL, 0, NULL }
1199    
1200 harbaum 191 /* -- the view submenu -- */
1201 harbaum 242 static const menu_entry_t submenu_view_entries[] = {
1202 harbaum 231 #ifndef ZOOM_BUTTONS
1203 harbaum 188 SIMPLE_ENTRY("Zoom in", cb_menu_zoomin),
1204     SIMPLE_ENTRY("Zoom out", cb_menu_zoomout),
1205 harbaum 231 #endif
1206 harbaum 188 /* --- */
1207     SIMPLE_ENTRY("Style", cb_menu_style),
1208     /* --- */
1209 harbaum 249 #ifndef DETAIL_POPUP
1210 harbaum 188 SIMPLE_ENTRY("Normal details", cb_menu_view_detail_normal),
1211     SIMPLE_ENTRY("More details", cb_menu_view_detail_inc),
1212     SIMPLE_ENTRY("Less details", cb_menu_view_detail_dec),
1213 harbaum 249 #endif
1214 harbaum 188 /* --- */
1215     DISABLED_ENTRY("Hide selected", cb_menu_map_hide_sel, menu_item_map_hide_sel),
1216     DISABLED_ENTRY("Show all", cb_menu_map_show_all, menu_item_map_show_all),
1217     /* --- */
1218 harbaum 190 TOGGLE_ENTRY("No icons", cb_menu_map_no_icons, no_icon_get_toggle),
1219 harbaum 188
1220     LAST_ENTRY
1221     };
1222    
1223 harbaum 242 static const submenu_t submenu_view = {
1224 harbaum 244 "View", submenu_view_entries,
1225     sizeof(submenu_view_entries)/sizeof(menu_entry_t)-1
1226 harbaum 242 };
1227    
1228 harbaum 191 /* -- the map submenu -- */
1229 harbaum 242 static const menu_entry_t submenu_map_entries[] = {
1230 harbaum 192 ENABLED_ENTRY("Upload", cb_menu_upload, menu_item_map_upload),
1231     SIMPLE_ENTRY("Download", cb_menu_download),
1232 harbaum 244 // ENABLED_ENTRY("Save changes", cb_menu_save_changes,
1233     // menu_item_map_save_changes),
1234 harbaum 242 ENABLED_ENTRY("Undo all", cb_menu_undo_changes,
1235     menu_item_map_undo_changes),
1236 harbaum 192 ENABLED_ENTRY("Relations", cb_menu_osm_relations,
1237 harbaum 242 menu_item_map_relations),
1238 harbaum 191
1239     LAST_ENTRY
1240     };
1241    
1242 harbaum 242 static const submenu_t submenu_map = {
1243 harbaum 244 "Map", submenu_map_entries,
1244     sizeof(submenu_map_entries)/sizeof(menu_entry_t)-1
1245 harbaum 242 };
1246    
1247 harbaum 188 /* -- the wms submenu -- */
1248 harbaum 242 static const menu_entry_t submenu_wms_entries[] = {
1249 harbaum 188 SIMPLE_ENTRY("Import", cb_menu_wms_import),
1250     DISABLED_ENTRY("Clear", cb_menu_wms_clear, menu_item_wms_clear),
1251     DISABLED_ENTRY("Adjust", cb_menu_wms_adjust, menu_item_wms_adjust),
1252    
1253     LAST_ENTRY
1254     };
1255    
1256 harbaum 242 static const submenu_t submenu_wms = {
1257 harbaum 244 "WMS", submenu_wms_entries,
1258     sizeof(submenu_wms_entries)/sizeof(menu_entry_t)-1
1259 harbaum 242 };
1260    
1261 harbaum 190 /* -- the track submenu -- */
1262 harbaum 242 static const menu_entry_t submenu_track_entries[] = {
1263 harbaum 190 ENABLED_ENTRY("Import", cb_menu_track_import, track.menu_item_track_import),
1264     DISABLED_ENTRY("Export", cb_menu_track_export, track.menu_item_track_export),
1265     DISABLED_ENTRY("Clear", cb_menu_track_clear, track.menu_item_track_clear),
1266     ENABLED_TOGGLE_ENTRY("GPS enable", cb_menu_track_enable_gps,
1267     enable_gps_get_toggle, track.menu_item_track_enable_gps),
1268     DISABLED_TOGGLE_ENTRY("GPS follow", cb_menu_track_follow_gps,
1269     follow_gps_get_toggle, track.menu_item_track_follow_gps),
1270 harbaum 188
1271 harbaum 190 LAST_ENTRY
1272     };
1273 harbaum 188
1274 harbaum 242 static const submenu_t submenu_track = {
1275 harbaum 244 "Track", submenu_track_entries,
1276     sizeof(submenu_track_entries)/sizeof(menu_entry_t)-1
1277 harbaum 242 };
1278 harbaum 188
1279 harbaum 242
1280 harbaum 190 /* -- the applications main menu -- */
1281     static const menu_entry_t main_menu[] = {
1282 harbaum 191 SIMPLE_ENTRY("About", cb_menu_about),
1283     SIMPLE_ENTRY("Project", cb_menu_project_open),
1284     ENABLED_ENTRY("View", on_submenu_view_clicked, submenu_view),
1285     ENABLED_ENTRY("Map", on_submenu_map_clicked, submenu_map),
1286     ENABLED_ENTRY("WMS", on_submenu_wms_clicked, submenu_wms),
1287     ENABLED_ENTRY("Track", on_submenu_track_clicked, track.submenu_track),
1288 harbaum 188
1289 harbaum 190 LAST_ENTRY
1290     };
1291 harbaum 188
1292 harbaum 190 void menu_create(appdata_t *appdata) {
1293     HildonAppMenu *menu = HILDON_APP_MENU(hildon_app_menu_new());
1294 harbaum 191
1295 harbaum 190 /* build menu/submenus */
1296     menu = HILDON_APP_MENU(app_menu_create(appdata, main_menu));
1297 harbaum 242 appdata->app_menu_wms = app_submenu_create(appdata, &submenu_wms);
1298 harbaum 228 g_object_ref(appdata->app_menu_wms);
1299 harbaum 242 appdata->app_menu_map = app_submenu_create(appdata, &submenu_map);
1300 harbaum 228 g_object_ref(appdata->app_menu_map);
1301 harbaum 242 appdata->app_menu_view = app_submenu_create(appdata, &submenu_view);
1302 harbaum 228 g_object_ref(appdata->app_menu_view);
1303 harbaum 242 appdata->app_menu_track = app_submenu_create(appdata, &submenu_track);
1304 harbaum 228 g_object_ref(appdata->app_menu_track);
1305 harbaum 188
1306 harbaum 191 /* enable/disable some entries according to settings */
1307 harbaum 192 if(appdata && appdata->settings)
1308     gtk_widget_set_sensitive(appdata->track.menu_item_track_follow_gps,
1309     appdata->settings->enable_gps);
1310 harbaum 191
1311 harbaum 190 hildon_window_set_app_menu(HILDON_WINDOW(appdata->window), menu);
1312 harbaum 188 }
1313 harbaum 242
1314     void menu_cleanup(appdata_t *appdata) {
1315     submenu_cleanup(appdata->app_menu_view);
1316     submenu_cleanup(appdata->app_menu_map);
1317     submenu_cleanup(appdata->app_menu_wms);
1318     submenu_cleanup(appdata->app_menu_track);
1319     }
1320 harbaum 188 #endif
1321    
1322 harbaum 1 /********************* end of menu **********************/
1323    
1324 achadwick 55 #ifdef UISPECIFIC_MENU_HAS_ACCELS
1325     #define ACCELS_FILE "accels"
1326 harbaum 1
1327 achadwick 55 static void menu_accels_load(appdata_t *appdata) {
1328     char *accels_file = g_strdup_printf("%s/" ACCELS_FILE,
1329     appdata->settings->base_path);
1330     gtk_accel_map_load(accels_file);
1331     g_free(accels_file);
1332     }
1333    
1334     static void menu_accels_save(appdata_t *appdata) {
1335     char *accels_file = g_strdup_printf("%s" ACCELS_FILE,
1336     appdata->settings->base_path);
1337     gtk_accel_map_save(accels_file);
1338     g_free(accels_file);
1339     }
1340    
1341     #endif
1342    
1343    
1344 harbaum 1 void cleanup(appdata_t *appdata) {
1345 achadwick 55 #ifdef UISPECIFIC_MENU_HAS_ACCELS
1346     menu_accels_save(appdata);
1347     #endif
1348    
1349 harbaum 1 settings_save(appdata->settings);
1350    
1351     #ifdef USE_HILDON
1352     if(appdata->osso_context)
1353     osso_deinitialize(appdata->osso_context);
1354    
1355     appdata->program = NULL;
1356     #endif
1357    
1358     printf("waiting for gtk to shut down ");
1359    
1360     /* let gtk clean up first */
1361     while(gtk_events_pending()) {
1362     putchar('.');
1363     gtk_main_iteration();
1364     }
1365    
1366     printf(" ok\n");
1367    
1368     /* save project file */
1369     if(appdata->project)
1370     project_save(GTK_WIDGET(appdata->window), appdata->project);
1371    
1372     map_remove_bg_image(appdata->map);
1373    
1374     osm_free(&appdata->icon, appdata->osm);
1375 harbaum 271 appdata->osm = NULL;
1376 harbaum 1
1377     curl_global_cleanup();
1378    
1379     josm_presets_free(appdata->presets);
1380    
1381     icon_free_all(&appdata->icon);
1382    
1383     gps_release(appdata);
1384    
1385     settings_free(appdata->settings);
1386    
1387     statusbar_free(appdata->statusbar);
1388    
1389     iconbar_free(appdata->iconbar);
1390    
1391     project_free(appdata->project);
1392    
1393 harbaum 188 if(appdata->menu_item_map_undo)
1394 harbaum 238 undo_free(appdata->osm, appdata->undo.state);
1395 harbaum 54
1396 harbaum 242 menu_cleanup(appdata);
1397    
1398 harbaum 1 puts("everything is gone");
1399     }
1400    
1401     void on_window_destroy (GtkWidget *widget, gpointer data) {
1402     appdata_t *appdata = (appdata_t*)data;
1403    
1404     gtk_main_quit();
1405     appdata->window = NULL;
1406     }
1407    
1408     gboolean on_window_key_press(GtkWidget *widget,
1409     GdkEventKey *event, gpointer data) {
1410     appdata_t *appdata = (appdata_t*)data;
1411     int handled = FALSE;
1412    
1413 harbaum 190 // printf("key event with keyval %x\n", event->keyval);
1414    
1415 harbaum 1 // the map handles some keys on its own ...
1416     switch(event->keyval) {
1417    
1418 harbaum 188 #if !defined(USE_HILDON) || (MAEMO_VERSION_MAJOR < 5)
1419 harbaum 22 #ifdef USE_HILDON
1420     /* this is in fact a mapping to GDK_F6 */
1421 harbaum 1 case HILDON_HARDKEY_FULLSCREEN:
1422 harbaum 22 #else
1423     case GDK_F11:
1424     #endif
1425     if(!gtk_check_menu_item_get_active(
1426     GTK_CHECK_MENU_ITEM(appdata->menu_item_view_fullscreen))) {
1427     gtk_window_fullscreen(GTK_WINDOW(appdata->window));
1428 harbaum 1 gtk_check_menu_item_set_active(
1429 harbaum 22 GTK_CHECK_MENU_ITEM(appdata->menu_item_view_fullscreen), TRUE);
1430     } else {
1431 harbaum 1 gtk_window_unfullscreen(GTK_WINDOW(appdata->window));
1432 harbaum 22 gtk_check_menu_item_set_active(
1433     GTK_CHECK_MENU_ITEM(appdata->menu_item_view_fullscreen), FALSE);
1434     }
1435    
1436     handled = TRUE;
1437 harbaum 1 break;
1438 harbaum 188 #endif
1439 harbaum 1 }
1440    
1441     /* forward unprocessed key presses to map */
1442     if(!handled && appdata->project && appdata->osm)
1443     handled = map_key_press_event(appdata, event);
1444    
1445     return handled;
1446     }
1447    
1448 harbaum 254 #if (MAEMO_VERSION_MAJOR == 5) && !defined(__i386__)
1449     /* get access to zoom buttons */
1450     static void
1451     on_window_realize(GtkWidget *widget, appdata_t *appdata) {
1452     if (widget->window) {
1453     unsigned char value = 1;
1454     Atom hildon_zoom_key_atom =
1455     gdk_x11_get_xatom_by_name("_HILDON_ZOOM_KEY_ATOM"),
1456     integer_atom = gdk_x11_get_xatom_by_name("INTEGER");
1457     Display *dpy =
1458     GDK_DISPLAY_XDISPLAY(gdk_drawable_get_display(widget->window));
1459     Window w = GDK_WINDOW_XID(widget->window);
1460    
1461     XChangeProperty(dpy, w, hildon_zoom_key_atom,
1462     integer_atom, 8, PropModeReplace, &value, 1);
1463     }
1464     }
1465     #endif
1466    
1467 harbaum 1 int main(int argc, char *argv[]) {
1468     appdata_t appdata;
1469    
1470     /* init appdata */
1471     memset(&appdata, 0, sizeof(appdata));
1472    
1473     printf("Using locale for %s in %s\n", PACKAGE, LOCALEDIR);
1474    
1475     setlocale(LC_ALL, "");
1476     bindtextdomain(PACKAGE, LOCALEDIR);
1477     bind_textdomain_codeset(PACKAGE, "UTF-8");
1478     textdomain(PACKAGE);
1479    
1480     /* Must initialize libcurl before any threads are started */
1481     curl_global_init(CURL_GLOBAL_ALL);
1482    
1483     g_thread_init(NULL);
1484    
1485 harbaum 118 gtk_init (&argc, &argv);
1486    
1487 harbaum 1 gps_init(&appdata);
1488    
1489     #ifdef USE_HILDON
1490     printf("Installing osso context for \"org.harbaum." PACKAGE "\"\n");
1491     appdata.osso_context = osso_initialize("org.harbaum."PACKAGE,
1492     VERSION, TRUE, NULL);
1493     if(appdata.osso_context == NULL)
1494     fprintf(stderr, "error initiating osso context\n");
1495    
1496     dbus_register(&appdata);
1497     #endif
1498    
1499     #ifdef USE_HILDON
1500     /* Create the hildon program and setup the title */
1501     appdata.program = HILDON_PROGRAM(hildon_program_get_instance());
1502     g_set_application_name("OSM2Go");
1503    
1504     /* Create HildonWindow and set it to HildonProgram */
1505 harbaum 225 #if MAEMO_VERSION_MAJOR < 5
1506 harbaum 1 appdata.window = HILDON_WINDOW(hildon_window_new());
1507 harbaum 225 #else
1508     appdata.window = HILDON_WINDOW(hildon_stackable_window_new());
1509     #endif
1510 harbaum 1 hildon_program_add_window(appdata.program, appdata.window);
1511 harbaum 190
1512 harbaum 249 /* try to enable the zoom buttons. don't do this on x86 as it breaks */
1513     /* at runtime with cygwin x */
1514     #if (MAEMO_VERSION_MAJOR == 5) && !defined(__i386__)
1515 harbaum 254 g_signal_connect(G_OBJECT(appdata.window), "realize",
1516     G_CALLBACK(on_window_realize), &appdata);
1517     #endif // MAEMO_VERSION
1518 harbaum 190
1519 harbaum 1 #else
1520     /* Create a Window. */
1521     appdata.window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
1522     gtk_window_set_title(GTK_WINDOW(appdata.window), "OSM2Go");
1523     /* Set a decent default size for the window. */
1524     gtk_window_set_default_size(GTK_WINDOW(appdata.window),
1525     DEFAULT_WIDTH, DEFAULT_HEIGHT);
1526     gtk_window_set_icon(GTK_WINDOW(appdata.window),
1527     icon_load(&appdata.icon, PACKAGE));
1528     #endif
1529    
1530     g_signal_connect(G_OBJECT(appdata.window), "destroy",
1531     G_CALLBACK(on_window_destroy), &appdata);
1532    
1533     g_signal_connect(G_OBJECT(appdata.window), "key_press_event",
1534     G_CALLBACK(on_window_key_press), &appdata);
1535    
1536 harbaum 14 /* user specific init */
1537     appdata.settings = settings_load();
1538    
1539 harbaum 1 appdata.vbox = gtk_vbox_new(FALSE,0);
1540     menu_create(&appdata);
1541 achadwick 55 #ifdef UISPECIFIC_MENU_HAS_ACCELS
1542     menu_accels_load(&appdata);
1543     #endif
1544 harbaum 1
1545     /* ----------------------- setup main window ---------------- */
1546    
1547     GtkWidget *hbox = gtk_hbox_new(FALSE,0);
1548     GtkWidget *vbox = gtk_vbox_new(FALSE,0);
1549    
1550     #ifdef PORTRAIT
1551     gtk_box_pack_start(GTK_BOX(vbox), iconbar_new(&appdata), FALSE, FALSE, 0);
1552     #endif
1553 harbaum 22
1554     /* generate main map view */
1555     GtkWidget *map = map_new(&appdata);
1556     if(!map) {
1557     cleanup(&appdata);
1558     return -1;
1559     }
1560    
1561     gtk_box_pack_start(GTK_BOX(vbox), map, TRUE, TRUE, 0);
1562 harbaum 188
1563 harbaum 246 #if defined(ZOOM_BUTTONS) || defined(DETAIL_POPUP)
1564 harbaum 195 GtkWidget *zhbox = gtk_hbox_new(FALSE, 0);
1565     gtk_box_pack_start_defaults(GTK_BOX(zhbox), statusbar_new(&appdata));
1566 harbaum 246 #endif
1567 harbaum 195
1568 harbaum 246 #ifdef DETAIL_POPUP
1569     /* ---- detail popup ---- */
1570     appdata.btn_detail_popup = gtk_button_new();
1571     gtk_button_set_image(GTK_BUTTON(appdata.btn_detail_popup),
1572 harbaum 259 gtk_image_new_from_stock(GTK_STOCK_EDIT, GTK_ICON_SIZE_MENU));
1573 harbaum 246 g_signal_connect(appdata.btn_detail_popup, "clicked",
1574 harbaum 249 G_CALLBACK(scale_popup), &appdata);
1575 harbaum 246 gtk_box_pack_start(GTK_BOX(zhbox), appdata.btn_detail_popup, FALSE, FALSE, 0);
1576     #endif
1577    
1578     #ifdef ZOOM_BUTTONS
1579 harbaum 224 /* ---- add zoom out button right of statusbar ---- */
1580     appdata.btn_zoom_out = gtk_button_new();
1581     gtk_button_set_image(GTK_BUTTON(appdata.btn_zoom_out),
1582     gtk_image_new_from_stock(GTK_STOCK_ZOOM_OUT, GTK_ICON_SIZE_MENU));
1583     g_signal_connect(appdata.btn_zoom_out, "clicked",
1584     G_CALLBACK(cb_menu_zoomout), &appdata);
1585     gtk_box_pack_start(GTK_BOX(zhbox), appdata.btn_zoom_out, FALSE, FALSE, 0);
1586    
1587 harbaum 195 /* ---- add zoom in button right of statusbar ---- */
1588     appdata.btn_zoom_in = gtk_button_new();
1589     gtk_button_set_image(GTK_BUTTON(appdata.btn_zoom_in),
1590 harbaum 224 gtk_image_new_from_stock(GTK_STOCK_ZOOM_IN, GTK_ICON_SIZE_MENU));
1591     g_signal_connect(appdata.btn_zoom_in, "clicked",
1592     G_CALLBACK(cb_menu_zoomin), &appdata);
1593 harbaum 195 gtk_box_pack_start(GTK_BOX(zhbox), appdata.btn_zoom_in, FALSE, FALSE, 0);
1594 harbaum 246 #endif
1595 harbaum 195
1596 harbaum 246 #if defined(ZOOM_BUTTONS) || defined(DETAIL_POPUP)
1597 harbaum 195 gtk_box_pack_start(GTK_BOX(vbox), zhbox, FALSE, FALSE, 0);
1598     #else
1599 harbaum 1 gtk_box_pack_start(GTK_BOX(vbox), statusbar_new(&appdata), FALSE, FALSE, 0);
1600 harbaum 195 #endif
1601 harbaum 1
1602     #ifndef PORTRAIT
1603     gtk_box_pack_start(GTK_BOX(hbox), iconbar_new(&appdata), FALSE, FALSE, 0);
1604     #endif
1605     gtk_box_pack_start(GTK_BOX(hbox), vbox, TRUE, TRUE, 0);
1606    
1607     gtk_box_pack_start(GTK_BOX(appdata.vbox), hbox, TRUE, TRUE, 0);
1608    
1609     gtk_container_add(GTK_CONTAINER(appdata.window), appdata.vbox);
1610    
1611     gtk_widget_show_all(GTK_WIDGET(appdata.window));
1612    
1613     appdata.presets = josm_presets_load();
1614    
1615     /* let gtk do its thing before loading the data, */
1616     /* so the user sees something */
1617 harbaum 179 while(gtk_events_pending())
1618 harbaum 1 gtk_main_iteration();
1619    
1620     /* load project if one is specified in the settings */
1621     if(appdata.settings->project)
1622     project_load(&appdata, appdata.settings->project);
1623    
1624 harbaum 4 main_ui_enable(&appdata);
1625 harbaum 1
1626 harbaum 156 /* start GPS if enabled by config */
1627     if(appdata.settings && appdata.settings->enable_gps)
1628     track_enable_gps(&appdata, TRUE);
1629    
1630 harbaum 179 /* again let the ui do its thing */
1631     while(gtk_events_pending())
1632     gtk_main_iteration();
1633    
1634     /* start to interact with the user now that the gui is running */
1635     if(appdata.settings->first_run_demo) {
1636     messagef(GTK_WIDGET(appdata.window), _("Welcome to OSM2Go"),
1637     _("This is the first time you run OSM2Go. "
1638     "A demo project has been loaded to get you "
1639     "started. You can play around with this demo as much "
1640     "as you like. However, you cannot upload or download "
1641     "the demo project.\n\n"
1642     "In order to start working on real data you'll have "
1643     "to setup a new project and enter your OSM user name "
1644     "and password. You'll then be able to download the "
1645     "latest data from OSM and upload your changes into "
1646     "the OSM main database."
1647     ));
1648     }
1649    
1650 harbaum 1 /* ------------ jump into main loop ---------------- */
1651     gtk_main();
1652    
1653 harbaum 4 puts("gtk_main() left");
1654    
1655 harbaum 1 track_save(appdata.project, appdata.track.track);
1656 harbaum 118 track_clear(&appdata, appdata.track.track);
1657 harbaum 156 appdata.track.track = NULL;
1658 harbaum 1
1659     /* save a diff if there are dirty entries */
1660     diff_save(appdata.project, appdata.osm);
1661    
1662     cleanup(&appdata);
1663    
1664     return 0;
1665     }
1666 achadwick 55
1667     // vim:et:ts=8:sw=2:sts=2:ai