2 * Copyright (C) 2006, 2007 John Costigan.
4 * POI and GPS-Info code originally written by Cezary Jackiewicz.
6 * Default map data provided by http://www.openstreetmap.org/
8 * This file is part of Maemo Mapper.
10 * Maemo Mapper is free software: you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation, either version 3 of the License, or
13 * (at your option) any later version.
15 * Maemo Mapper is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with Maemo Mapper. If not, see <http://www.gnu.org/licenses/>.
33 #include <dbus/dbus-glib.h>
36 #include <gconf/gconf-client.h>
38 #ifdef MAEMO_CHANGES /* probably not the best macro to check for here */
39 # include <device_symbols.h>
43 # include <conicconnection.h>
44 # include <conicconnectionevent.h>
48 # include <hildon/hildon-program.h>
49 # include <hildon/hildon-banner.h>
51 # include <hildon-widgets/hildon-program.h>
52 # include <hildon-widgets/hildon-banner.h>
74 static void osso_cb_hw_state(osso_hw_state_t *state, gpointer data);
76 static HildonProgram *_program = NULL;
79 static ConIcConnection *_conic_conn = NULL;
80 static gboolean _conic_is_connecting = FALSE;
81 static gboolean _conic_conn_failed = FALSE;
82 static GMutex *_conic_connection_mutex = NULL;
83 static GCond *_conic_connection_cond = NULL;
86 /* Dynamically-sized in-memory map cache. */
87 static size_t _map_cache_size = (32*1024*1024);
88 static gboolean _map_cache_enabled = TRUE;
92 conic_conn_event(ConIcConnection *connection, ConIcConnectionEvent *event)
94 ConIcConnectionStatus status;
95 printf("%s()\n", __PRETTY_FUNCTION__);
97 g_mutex_lock(_conic_connection_mutex);
99 status = con_ic_connection_event_get_status(event);
101 if((_conic_is_connected = (status == CON_IC_STATUS_CONNECTED)))
103 /* We're connected. */
104 _conic_conn_failed = FALSE;
105 if(_download_banner != NULL)
106 gtk_widget_show(_download_banner);
110 /* We're not connected. */
111 /* Mark as a failed connection, if we had been trying to connect. */
112 _conic_conn_failed = _conic_is_connecting;
113 if(_download_banner != NULL)
114 gtk_widget_hide(_download_banner);
117 _conic_is_connecting = FALSE; /* No longer trying to connect. */
118 g_cond_broadcast(_conic_connection_cond);
119 g_mutex_unlock(_conic_connection_mutex);
121 vprintf("%s(): return\n", __PRETTY_FUNCTION__);
126 conic_recommend_connected()
128 printf("%s()\n", __PRETTY_FUNCTION__);
130 #if defined(__arm__) && defined(CONIC)
131 g_mutex_lock(_conic_connection_mutex);
132 if(!_conic_is_connecting)
134 /* Fire up a connection request. */
135 con_ic_connection_connect(_conic_conn, CON_IC_CONNECT_FLAG_NONE);
136 _conic_is_connecting = TRUE;
138 g_mutex_unlock(_conic_connection_mutex);
141 vprintf("%s(): return\n", __PRETTY_FUNCTION__);
145 conic_ensure_connected()
147 printf("%s()\n", __PRETTY_FUNCTION__);
149 #if defined(__arm__) && defined(CONIC)
150 while(_window && !_conic_is_connected)
152 g_mutex_lock(_conic_connection_mutex);
153 /* If we're not connected, and if we're not connecting, and if we're
154 * not in the wake of a connection failure, then try to connect. */
155 if(!_conic_is_connected && !_conic_is_connecting &&!_conic_conn_failed)
157 /* Fire up a connection request. */
158 con_ic_connection_connect(_conic_conn, CON_IC_CONNECT_FLAG_NONE);
159 _conic_is_connecting = TRUE;
161 g_cond_wait(_conic_connection_cond, _conic_connection_mutex);
162 g_mutex_unlock(_conic_connection_mutex);
165 _conic_is_connected = TRUE;
168 vprintf("%s(): return %d\n", __PRETTY_FUNCTION__,
169 _window && _conic_is_connected);
170 return _window && _conic_is_connected;
174 * Save state and destroy all non-UI elements created by this program in
175 * preparation for exiting.
178 maemo_mapper_destroy()
180 printf("%s()\n", __PRETTY_FUNCTION__);
182 /* _program and widgets have already been destroyed. */
193 g_mutex_lock(_mut_priority_mutex);
194 _mut_priority_tree = g_tree_new((GCompareFunc)mut_priority_comparefunc);
195 g_mutex_unlock(_mut_priority_mutex);
197 /* Allow remaining downloads to finish. */
199 g_mutex_lock(_conic_connection_mutex);
200 g_cond_broadcast(_conic_connection_cond);
201 g_mutex_unlock(_conic_connection_mutex);
203 g_thread_pool_free(_mut_thread_pool, TRUE, TRUE);
209 g_mutex_lock(_mapdb_mutex);
210 sqlite3_close(_curr_repo->db);
211 _curr_repo->db = NULL;
212 g_mutex_unlock(_mapdb_mutex);
214 g_mutex_lock(_mapdb_mutex);
218 /* /\* perform reorganization for layers which are auto refreshed *\/ */
219 /* if (repo_p->layer_level && repo_p->layer_refresh_interval) */
220 /* gdbm_reorganize (repo_p->db); */
221 gdbm_close(repo_p->db);
224 repo_p = repo_p->layers;
226 g_mutex_unlock(_mapdb_mutex);
233 vprintf("%s(): return\n", __PRETTY_FUNCTION__);
236 // Called once per second
237 gboolean timer_callback (gpointer data) {
240 static int inet_beacon_count = 0;
241 static int inet_aprs_filter = 0;
242 static int tty_beacon_count = 0;
246 // Check if we need to resent the filter every 5 minutes
247 // Note - this should really be dependent on speed and/or range
248 if(_aprs_inet_enable && inet_aprs_filter > (60*5))
250 // Currently this only needs to be sent on connection
251 //update_aprs_inet_options(FALSE);
252 inet_aprs_filter = 0;
255 if(_aprs_inet_enable && _aprs_enable_inet_tx && _aprs_inet_beacon_interval > 0 && _aprs_inet_state == RCVR_UP)
259 if(inet_beacon_count >= _aprs_inet_beacon_interval)
261 // Send inet APRS beacon
262 aprs_send_beacon(APRS_PORT_INET);
263 //g_idle_add((GSourceFunc)aprs_send_beacon, APRS_PORT_INET);
264 //fprintf(stderr, "timer %u, %u\n", inet_beacon_count, _aprs_inet_beacon_interval);
265 inet_beacon_count = 0;
270 if(_aprs_tty_enable && _aprs_enable_tty_tx )
272 // Send tty APRS beacon
274 if(tty_beacon_count >= _aprs_tty_beacon_interval && _aprs_tty_beacon_interval > 0)
276 // Send inet APRS beacon
277 aprs_send_beacon(APRS_PORT_TTY);
279 //g_idle_add((GSourceFunc)aprs_send_beacon_inet, NULL);
281 tty_beacon_count = 0;
291 #endif //INCLUDE_APRS
293 return TRUE; // Continue timer
296 // Start a one second timer - this can be used to execute any periodic tasks
299 g_timeout_add(1000 , timer_callback, NULL);
303 * Initialize everything required in preparation for calling gtk_main().
306 maemo_mapper_init(gint argc, gchar **argv)
308 GtkWidget *hbox, *label, *vbox;
309 printf("%s()\n", __PRETTY_FUNCTION__);
311 /* Set enum-based constants. */
312 UNITS_ENUM_TEXT[UNITS_KM] = _("km");
313 UNITS_ENUM_TEXT[UNITS_MI] = _("mi.");
314 UNITS_ENUM_TEXT[UNITS_NM] = _("n.m.");
316 ROTATE_DIR_ENUM_TEXT[ROTATE_DIR_UP] = _("Up");
317 ROTATE_DIR_ENUM_TEXT[ROTATE_DIR_RIGHT] = _("Right");
318 ROTATE_DIR_ENUM_TEXT[ROTATE_DIR_DOWN] = _("Down");
319 ROTATE_DIR_ENUM_TEXT[ROTATE_DIR_LEFT] = _("Left");
321 UNBLANK_ENUM_TEXT[UNBLANK_WITH_GPS] = _("When Receiving Any GPS Data");
322 UNBLANK_ENUM_TEXT[UNBLANK_WHEN_MOVING] = _("When Moving");
323 UNBLANK_ENUM_TEXT[UNBLANK_FULLSCREEN] = _("When Moving (Full Screen Only)");
324 UNBLANK_ENUM_TEXT[UNBLANK_WAYPOINT] = _("When Approaching a Waypoint");
325 UNBLANK_ENUM_TEXT[UNBLANK_NEVER] = _("Never");
327 INFO_FONT_ENUM_TEXT[INFO_FONT_XXSMALL] = "xx-small";
328 INFO_FONT_ENUM_TEXT[INFO_FONT_XSMALL] = "x-small";
329 INFO_FONT_ENUM_TEXT[INFO_FONT_SMALL] = "small";
330 INFO_FONT_ENUM_TEXT[INFO_FONT_MEDIUM] = "medium";
331 INFO_FONT_ENUM_TEXT[INFO_FONT_LARGE] = "large";
332 INFO_FONT_ENUM_TEXT[INFO_FONT_XLARGE] = "x-large";
333 INFO_FONT_ENUM_TEXT[INFO_FONT_XXLARGE] = "xx-large";
335 #ifdef MAEMO_CHANGES /* probably not the best macro to check for here */
336 CUSTOM_KEY_ICON[CUSTOM_KEY_UP] = HWK_BUTTON_UP;
337 CUSTOM_KEY_ICON[CUSTOM_KEY_LEFT] = HWK_BUTTON_LEFT;
338 CUSTOM_KEY_ICON[CUSTOM_KEY_DOWN] = HWK_BUTTON_DOWN;
339 CUSTOM_KEY_ICON[CUSTOM_KEY_RIGHT] = HWK_BUTTON_RIGHT;
340 CUSTOM_KEY_ICON[CUSTOM_KEY_SELECT] = HWK_BUTTON_SELECT;
341 CUSTOM_KEY_ICON[CUSTOM_KEY_INCREASE] = HWK_BUTTON_INCREASE;
342 CUSTOM_KEY_ICON[CUSTOM_KEY_DECREASE] = HWK_BUTTON_DECREASE;
343 CUSTOM_KEY_ICON[CUSTOM_KEY_FULLSCREEN] = HWK_BUTTON_VIEW;
344 CUSTOM_KEY_ICON[CUSTOM_KEY_ESC] = HWK_BUTTON_CANCEL;
346 CUSTOM_KEY_ICON[CUSTOM_KEY_UP] = "Up";
347 CUSTOM_KEY_ICON[CUSTOM_KEY_LEFT] = "Left";
348 CUSTOM_KEY_ICON[CUSTOM_KEY_DOWN] = "Down";
349 CUSTOM_KEY_ICON[CUSTOM_KEY_RIGHT] = "Right";
350 CUSTOM_KEY_ICON[CUSTOM_KEY_SELECT] = "Enter";
351 CUSTOM_KEY_ICON[CUSTOM_KEY_INCREASE] = "F7";
352 CUSTOM_KEY_ICON[CUSTOM_KEY_DECREASE] = "F8";
353 CUSTOM_KEY_ICON[CUSTOM_KEY_FULLSCREEN] = "F6";
354 CUSTOM_KEY_ICON[CUSTOM_KEY_ESC] = "Esc";
357 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_UP] = CUSTOM_ACTION_RESET_VIEW_ANGLE;
358 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_LEFT] =CUSTOM_ACTION_ROTATE_COUNTERCLOCKWISE;
359 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_DOWN] = CUSTOM_ACTION_TOGGLE_AUTOROTATE;
360 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_RIGHT] = CUSTOM_ACTION_ROTATE_CLOCKWISE;
361 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_SELECT] = CUSTOM_ACTION_TOGGLE_AUTOCENTER;
362 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_INCREASE] = CUSTOM_ACTION_ZOOM_IN;
363 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_DECREASE] = CUSTOM_ACTION_ZOOM_OUT;
364 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_FULLSCREEN]= CUSTOM_ACTION_TOGGLE_FULLSCREEN;
365 CUSTOM_KEY_DEFAULT[CUSTOM_KEY_ESC] = CUSTOM_ACTION_TOGGLE_TRACKS;
367 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_NORTH] = _("Pan North");
368 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_WEST] = _("Pan West");
369 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_SOUTH] = _("Pan South");
370 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_EAST] = _("Pan East");
371 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_UP] = _("Pan Up");
372 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_DOWN] = _("Pan Down");
373 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_LEFT] = _("Pan Left");
374 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_PAN_RIGHT] = _("Pan Right");
375 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_RESET_VIEW_ANGLE]
376 = _("Reset Viewing Angle");
377 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_ROTATE_CLOCKWISE]
378 = _("Rotate View Clockwise");
379 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_ROTATE_COUNTERCLOCKWISE]
380 = _("Rotate View Counter-Clockwise");
381 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_AUTOCENTER]
382 = _("Toggle Auto-Center");
383 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_AUTOROTATE]
384 = _("Toggle Auto-Rotate");
385 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_FULLSCREEN]
386 = _("Toggle Fullscreen");
387 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_ZOOM_IN] = _("Zoom In");
388 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_ZOOM_OUT] = _("Zoom Out");
389 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_TRACKING]
390 = _("Toggle Tracking");
391 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_TRACKS]
392 = _("Toggle Tracks/Routes");
393 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_SCALE] = _("Toggle Scale");
394 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_POI] = _("Toggle POIs");
395 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_CHANGE_REPO]
396 = _("Select Next Repository");
397 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_ROUTE_DISTNEXT]
398 = _("Show Distance to Next Waypoint");
399 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_ROUTE_DISTLAST]
400 = _("Show Distance to End of Route");
401 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TRACK_BREAK]=_("Insert Track Break");
402 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TRACK_CLEAR] = _("Clear Track");
403 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TRACK_DISTLAST]
404 = _("Show Distance from Last Break");
405 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TRACK_DISTFIRST]
406 = _("Show Distance from Beginning");
407 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_GPS] = _("Toggle GPS");
408 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_GPSINFO]=_("Toggle GPS Info");
409 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_SPEEDLIMIT]
410 = _("Toggle Speed Limit");
411 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_RESET_BLUETOOTH]
412 = _("Reset Bluetooth");
413 CUSTOM_ACTION_ENUM_TEXT[CUSTOM_ACTION_TOGGLE_LAYERS] = _("Toggle Layers");
415 DEG_FORMAT_ENUM_TEXT[DDPDDDDD].name = "-dd.ddddd°";
416 DEG_FORMAT_ENUM_TEXT[DDPDDDDD].short_field_1 = "Lat";
417 DEG_FORMAT_ENUM_TEXT[DDPDDDDD].long_field_1 = "Latitude";
418 DEG_FORMAT_ENUM_TEXT[DDPDDDDD].short_field_2 = "Lon";
419 DEG_FORMAT_ENUM_TEXT[DDPDDDDD].long_field_2 = "Longitude";
420 DEG_FORMAT_ENUM_TEXT[DDPDDDDD].field_2_in_use = TRUE;
422 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM].name = "-dd°mm.mmm'";
423 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM].short_field_1 = "Lat";
424 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM].long_field_1 = "Latitude";
425 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM].short_field_2 = "Lon";
426 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM].long_field_2 = "Longitude";
427 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM].field_2_in_use = TRUE;
429 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS].name = "-dd°mm'ss.s\"";
430 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS].short_field_1 = "Lat";
431 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS].long_field_1 = "Latitude";
432 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS].short_field_2 = "Lon";
433 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS].long_field_2 = "Longitude";
434 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS].field_2_in_use = TRUE;
436 DEG_FORMAT_ENUM_TEXT[DDPDDDDD_NSEW].name = "dd.ddddd° S";
437 DEG_FORMAT_ENUM_TEXT[DDPDDDDD_NSEW].short_field_1 = "Lat";
438 DEG_FORMAT_ENUM_TEXT[DDPDDDDD_NSEW].long_field_1 = "Latitude";
439 DEG_FORMAT_ENUM_TEXT[DDPDDDDD_NSEW].short_field_2 = "Lon";
440 DEG_FORMAT_ENUM_TEXT[DDPDDDDD_NSEW].long_field_2 = "Longitude";
441 DEG_FORMAT_ENUM_TEXT[DDPDDDDD_NSEW].field_2_in_use = TRUE;
443 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM_NSEW].name = "dd°mm.mmm' S";
444 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM_NSEW].short_field_1 = "Lat";
445 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM_NSEW].long_field_1 = "Latitude";
446 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM_NSEW].short_field_2 = "Lon";
447 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM_NSEW].long_field_2 = "Longitude";
448 DEG_FORMAT_ENUM_TEXT[DD_MMPMMM_NSEW].field_2_in_use = TRUE;
450 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS_NSEW].name = "dd°mm'ss.s\" S";
451 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS_NSEW].short_field_1 = "Lat";
452 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS_NSEW].long_field_1 = "Latitude";
453 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS_NSEW].short_field_2 = "Lon";
454 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS_NSEW].long_field_2 = "Longitude";
455 DEG_FORMAT_ENUM_TEXT[DD_MM_SSPS_NSEW].field_2_in_use = TRUE;
457 DEG_FORMAT_ENUM_TEXT[NSEW_DDPDDDDD].name = "S dd.ddddd°";
458 DEG_FORMAT_ENUM_TEXT[NSEW_DDPDDDDD].short_field_1 = "Lat";
459 DEG_FORMAT_ENUM_TEXT[NSEW_DDPDDDDD].long_field_1 = "Latitude";
460 DEG_FORMAT_ENUM_TEXT[NSEW_DDPDDDDD].short_field_2 = "Lon";
461 DEG_FORMAT_ENUM_TEXT[NSEW_DDPDDDDD].long_field_2 = "Longitude";
462 DEG_FORMAT_ENUM_TEXT[NSEW_DDPDDDDD].field_2_in_use = TRUE;
464 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MMPMMM].name = "S dd° mm.mmm'";
465 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MMPMMM].short_field_1 = "Lat";
466 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MMPMMM].long_field_1 = "Latitude";
467 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MMPMMM].short_field_2 = "Lon";
468 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MMPMMM].long_field_2 = "Longitude";
469 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MMPMMM].field_2_in_use = TRUE;
471 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MM_SSPS].name = "S dd° mm' ss.s\"";
472 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MM_SSPS].short_field_1 = "Lat";
473 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MM_SSPS].long_field_1 = "Latitude";
474 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MM_SSPS].short_field_2 = "Lon";
475 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MM_SSPS].long_field_2 = "Longitude";
476 DEG_FORMAT_ENUM_TEXT[NSEW_DD_MM_SSPS].field_2_in_use = TRUE;
478 // Used by Radio Amateurs
479 DEG_FORMAT_ENUM_TEXT[IARU_LOC].name = "IARU Locator";
480 DEG_FORMAT_ENUM_TEXT[IARU_LOC].short_field_1 = "Locator";
481 DEG_FORMAT_ENUM_TEXT[IARU_LOC].long_field_1 = "Lacator";
482 DEG_FORMAT_ENUM_TEXT[IARU_LOC].short_field_2 = "";
483 DEG_FORMAT_ENUM_TEXT[IARU_LOC].long_field_2 = "";
484 DEG_FORMAT_ENUM_TEXT[IARU_LOC].field_2_in_use = FALSE;
487 DEG_FORMAT_ENUM_TEXT[UK_OSGB].name = "OSGB X,Y Grid";
488 DEG_FORMAT_ENUM_TEXT[UK_OSGB].short_field_1 = "X";
489 DEG_FORMAT_ENUM_TEXT[UK_OSGB].long_field_1 = "OS X";
490 DEG_FORMAT_ENUM_TEXT[UK_OSGB].short_field_2 = "Y";
491 DEG_FORMAT_ENUM_TEXT[UK_OSGB].long_field_2 = "OS Y";
492 DEG_FORMAT_ENUM_TEXT[UK_OSGB].field_2_in_use = TRUE;
494 DEG_FORMAT_ENUM_TEXT[UK_NGR].name = "OSGB Landranger Grid";
495 DEG_FORMAT_ENUM_TEXT[UK_NGR].short_field_1 = "GR";
496 DEG_FORMAT_ENUM_TEXT[UK_NGR].long_field_1 = "OS Grid";
497 DEG_FORMAT_ENUM_TEXT[UK_NGR].short_field_2 = "";
498 DEG_FORMAT_ENUM_TEXT[UK_NGR].long_field_2 = "";
499 DEG_FORMAT_ENUM_TEXT[UK_NGR].field_2_in_use = FALSE;
501 SPEED_LOCATION_ENUM_TEXT[SPEED_LOCATION_TOP_LEFT] = _("Top-Left");
502 SPEED_LOCATION_ENUM_TEXT[SPEED_LOCATION_TOP_RIGHT] = _("Top-Right");
503 SPEED_LOCATION_ENUM_TEXT[SPEED_LOCATION_BOTTOM_RIGHT] = _("Bottom-Right");
504 SPEED_LOCATION_ENUM_TEXT[SPEED_LOCATION_BOTTOM_LEFT] = _("Bottom-Left");
506 GPS_RCVR_ENUM_TEXT[GPS_RCVR_BT] = _("Bluetooth");
507 GPS_RCVR_ENUM_TEXT[GPS_RCVR_GPSD] = _("GPSD");
508 GPS_RCVR_ENUM_TEXT[GPS_RCVR_FILE] = _("File");
510 /* Set up track array (must be done before config). */
511 memset(&_track, 0, sizeof(_track));
512 memset(&_route, 0, sizeof(_route));
513 /* initialisation of paths is done in path_init() */
515 _mapdb_mutex = g_mutex_new();
516 _mut_priority_mutex = g_mutex_new();
517 _mouse_mutex = g_mutex_new();
520 _conic_connection_mutex = g_mutex_new();
521 _conic_connection_cond = g_cond_new();
525 map_cache_init(_map_cache_size);
527 /* Initialize _program. */
528 _program = HILDON_PROGRAM(hildon_program_get_instance());
529 g_set_application_name("Maemo Mapper");
531 /* Initialize _window. */
532 _window = GTK_WIDGET(hildon_window_new());
533 hildon_program_add_window(_program, HILDON_WINDOW(_window));
535 gtk_window_set_default_size(GTK_WINDOW(_window), 800, 480);
537 /* Lets go fullscreen if so requested in saved config */
539 gtk_window_fullscreen(GTK_WINDOW(_window));
542 /* Create and add widgets and supporting data. */
543 hbox = gtk_hbox_new(FALSE, 0);
544 gtk_container_add(GTK_CONTAINER(_window), hbox);
546 _gps_widget = gtk_frame_new("GPS Info");
547 gtk_container_add(GTK_CONTAINER(_gps_widget),
548 vbox = gtk_vbox_new(FALSE, 0));
549 gtk_widget_set_size_request(GTK_WIDGET(_gps_widget), 180, 0);
550 gtk_box_pack_start(GTK_BOX(hbox), _gps_widget, FALSE, TRUE, 0);
552 label = gtk_label_new(" ");
553 gtk_widget_set_size_request(GTK_WIDGET(label), -1, 10);
554 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, TRUE, 0);
556 _text_lat = gtk_label_new(" --- ");
557 gtk_widget_set_size_request(GTK_WIDGET(_text_lat), -1, 30);
558 gtk_box_pack_start(GTK_BOX(vbox), _text_lat, FALSE, TRUE, 0);
560 _text_lon = gtk_label_new(" --- ");
561 gtk_widget_set_size_request(GTK_WIDGET(_text_lon), -1, 30);
562 gtk_box_pack_start(GTK_BOX(vbox), _text_lon, FALSE, TRUE, 0);
564 _text_speed = gtk_label_new(" --- ");
565 gtk_widget_set_size_request(GTK_WIDGET(_text_speed), -1, 30);
566 gtk_box_pack_start(GTK_BOX(vbox), _text_speed, FALSE, TRUE, 0);
568 _text_alt = gtk_label_new(" --- ");
569 gtk_widget_set_size_request(GTK_WIDGET(_text_alt), -1, 30);
570 gtk_box_pack_start(GTK_BOX(vbox), _text_alt, FALSE, TRUE, 0);
572 label = gtk_label_new(" ");
573 gtk_widget_set_size_request(GTK_WIDGET(label), -1, 10);
574 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, TRUE, 0);
576 _sat_panel = gtk_drawing_area_new ();
577 gtk_widget_set_size_request (_sat_panel, -1, 100);
578 gtk_box_pack_start(GTK_BOX(vbox), _sat_panel, TRUE, TRUE, 0);
580 label = gtk_label_new(" ");
581 gtk_widget_set_size_request(GTK_WIDGET(label), -1, 10);
582 gtk_box_pack_start(GTK_BOX(vbox), label, FALSE, TRUE, 0);
584 _text_time = gtk_label_new("--:--:--");
585 gtk_widget_set_size_request(GTK_WIDGET(_text_time), -1, 30);
586 gtk_box_pack_start(GTK_BOX(vbox), _text_time, FALSE, TRUE, 0);
588 _heading_panel = gtk_drawing_area_new ();
589 gtk_widget_set_size_request (_heading_panel, -1, 100);
590 gtk_box_pack_start(GTK_BOX(vbox), _heading_panel, TRUE, TRUE, 0);
592 _map_widget = gtk_drawing_area_new();
594 gtk_box_pack_start(GTK_BOX(hbox), _map_widget, TRUE, TRUE, 0);
596 gtk_widget_show_all(hbox);
597 gps_show_info(); /* hides info, if necessary. */
599 gtk_widget_realize(_map_widget);
601 /* Tweak the foreground and background colors a little bit... */
605 GdkColormap *colormap = gtk_widget_get_colormap(_map_widget);
608 _map_widget->style->fg_gc[GTK_STATE_NORMAL],
610 gdk_colormap_query_color(colormap, values.foreground.pixel, &color);
611 gtk_widget_modify_fg(_map_widget, GTK_STATE_ACTIVE, &color);
614 _map_widget->style->bg_gc[GTK_STATE_NORMAL],
616 gdk_colormap_query_color(colormap, values.foreground.pixel, &color);
617 gtk_widget_modify_bg(_map_widget, GTK_STATE_ACTIVE, &color);
619 /* Use a black background for _map_widget, since missing tiles are
620 * also drawn with a black background. */
621 color.red = 0; color.green = 0; color.blue = 0;
622 gtk_widget_modify_bg(_map_widget,
623 GTK_STATE_NORMAL, &color);
626 _map_pixmap = gdk_pixmap_new(_map_widget->window, 1, 1, -1);
627 /* -1: use bit depth of widget->window. */
629 _map_pixbuf = gdk_pixbuf_new(GDK_COLORSPACE_RGB, FALSE, 8, 1, 1);
631 _mut_exists_table = g_hash_table_new(
632 (GHashFunc)mut_exists_hashfunc, (GEqualFunc)mut_exists_equalfunc);
633 _mut_priority_tree = g_tree_new((GCompareFunc)mut_priority_comparefunc);
635 _mut_thread_pool = g_thread_pool_new(
636 (GFunc)thread_proc_mut, NULL, NUM_DOWNLOAD_THREADS, FALSE, NULL);
637 _mrt_thread_pool = g_thread_pool_new(
638 (GFunc)thread_render_map, NULL, 1, FALSE, NULL);
640 /* Connect signals. */
641 g_signal_connect(G_OBJECT(_window), "destroy",
642 G_CALLBACK(gtk_main_quit), NULL);
644 memset(&_autoroute_data, 0, sizeof(_autoroute_data));
646 latlon2unit(_gps.lat, _gps.lon, _pos.unitx, _pos.unity);
648 /* Initialize our line styles. */
663 #endif //INCLUDE_APRS
665 /* If present, attempt to load the file specified on the command line. */
668 GnomeVFSResult vfs_result;
673 /* Get the selected filename. */
674 file_uri = gnome_vfs_make_uri_from_shell_arg(argv[1]);
676 if(GNOME_VFS_OK != (vfs_result = gnome_vfs_read_entire_file(
677 file_uri, &size, &buffer)))
679 gchar buffer[BUFFER_SIZE];
680 snprintf(buffer, sizeof(buffer),
681 "%s:\n%s", _("Failed to open file for reading"),
682 gnome_vfs_result_to_string(vfs_result));
683 popup_error(_window, buffer);
687 if(gpx_path_parse(&_route, buffer, size, 0))
689 path_save_route_to_db();
690 MACRO_BANNER_SHOW_INFO(_window, _("Route Opened"));
693 popup_error(_window, _("Error parsing GPX file."));
699 /* If we have a route, calculate the next point. */
700 route_find_nearest_point();
703 _conic_conn = con_ic_connection_new();
704 g_object_set(_conic_conn, "automatic-connection-events", TRUE, NULL);
705 g_signal_connect(G_OBJECT(_conic_conn), "connection-event",
706 G_CALLBACK(conic_conn_event), NULL);
709 g_idle_add((GSourceFunc)window_present, NULL);
712 osso_hw_set_event_cb(_osso, NULL, osso_cb_hw_state, NULL);
714 vprintf("%s(): return\n", __PRETTY_FUNCTION__);
718 osso_cb_hw_state_idle(osso_hw_state_t *state)
720 static gboolean _must_save_data = FALSE;
721 printf("%s(inact=%d, save=%d, shut=%d, memlow=%d, state=%d)\n",
722 __PRETTY_FUNCTION__, state->system_inactivity_ind,
723 state->save_unsaved_data_ind, state->shutdown_ind,
724 state->memory_low_ind, state->sig_device_mode_ind);
726 if(state->shutdown_ind)
728 maemo_mapper_destroy();
732 if(state->save_unsaved_data_ind)
735 _must_save_data = TRUE;
738 if(state->memory_low_ind)
740 // Disable the map cache and set the next max cache size to
741 // slightly less than the current cache size.
742 _map_cache_size = map_cache_resize(0) * 0.8;
743 _map_cache_enabled = FALSE;
747 if(!_map_cache_enabled)
749 // Restore the map cache.
750 map_cache_resize(_map_cache_size);
751 _map_cache_enabled = TRUE;
757 vprintf("%s(): return\n", __PRETTY_FUNCTION__);
762 osso_cb_hw_state(osso_hw_state_t *state, gpointer data)
764 printf("%s()\n", __PRETTY_FUNCTION__);
765 osso_hw_state_t *state_copy = g_new(osso_hw_state_t, 1);
766 memcpy(state_copy, state, sizeof(osso_hw_state_t));
767 g_idle_add((GSourceFunc)osso_cb_hw_state_idle, state_copy);
768 vprintf("%s(): return\n", __PRETTY_FUNCTION__);
772 main(gint argc, gchar *argv[])
774 printf("%s()\n", __PRETTY_FUNCTION__);
776 /* Initialize localization. */
777 setlocale(LC_ALL, "");
778 bindtextdomain(GETTEXT_PACKAGE, LOCALEDIR);
779 bind_textdomain_codeset(GETTEXT_PACKAGE, "UTF-8");
780 textdomain(GETTEXT_PACKAGE);
784 /* Initialize _osso. */
785 _osso = osso_initialize("com.gnuite.maemo_mapper", VERSION, TRUE, NULL);
788 g_printerr("osso_initialize failed.\n");
792 gtk_init(&argc, &argv);
796 gconf_init(argc, argv, NULL);
798 /* Init Gnome-VFS. */
802 /* This is just some helpful DBUS testing code. */
805 /* Try to set the center to a new lat/lon. */
806 GError *error = NULL;
809 DBusGConnection *bus;
812 bus = dbus_g_bus_get(DBUS_BUS_SESSION, &error);
815 g_printerr("Error: %s\n", error->message);
819 proxy = dbus_g_proxy_new_for_name(bus,
820 MM_DBUS_SERVICE, MM_DBUS_PATH, MM_DBUS_INTERFACE);
822 lat = g_ascii_strtod((argv[1]), &error_check);
823 if(error_check == argv[1])
825 g_printerr("Failed to parse string as float: %s\n", argv[1]);
829 lon = g_ascii_strtod((argv[2]), &error_check);
830 if(error_check == argv[2])
832 g_printerr("Failed to parse string as float: %s\n", argv[2]);
839 /* We are specifying a zoom. */
842 zoom = g_ascii_strtod((argv[3]), &error_check);
843 if(error_check == argv[3])
845 g_printerr("Failed to parse string as integer: %s\n", argv[3]);
848 if(!dbus_g_proxy_call(proxy, MM_DBUS_METHOD_SET_VIEW_POSITION,
850 G_TYPE_DOUBLE, lat, G_TYPE_DOUBLE, lon,
851 G_TYPE_INT, zoom, G_TYPE_INVALID,
855 g_printerr("Error: %s\n", error->message);
861 /* Not specifying a zoom. */
862 if(!dbus_g_proxy_call(proxy, MM_DBUS_METHOD_SET_VIEW_POSITION,
864 G_TYPE_DOUBLE, lat, G_TYPE_DOUBLE, lon, G_TYPE_INVALID,
868 g_printerr("Error: %s\n", error->message);
873 g_object_unref(proxy);
874 dbus_g_connection_unref(bus);
880 maemo_mapper_init(argc, argv);
884 maemo_mapper_destroy();
886 osso_deinitialize(_osso);
888 vprintf("%s(): return\n", __PRETTY_FUNCTION__);