X-Git-Url: http://pileus.org/git/?a=blobdiff_plain;f=src%2Fgis-viewer.c;h=a4d7dc5a28adcff982a3ca8d59e046f8570c57db;hb=2aecf6f80412c20d62796e4a380e1b6b0a84a1dc;hp=18ec589a8860ff6d064618b688ea904f5e62330c;hpb=194a225e4148805029672a21dfa1ceabad472364;p=grits diff --git a/src/gis-viewer.c b/src/gis-viewer.c index 18ec589..a4d7dc5 100644 --- a/src/gis-viewer.c +++ b/src/gis-viewer.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2009 Andy Spencer + * Copyright (C) 2009-2010 Andy Spencer * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -16,6 +16,7 @@ */ #include +#include #include #include @@ -28,7 +29,6 @@ /* Constants */ enum { SIG_TIME_CHANGED, - SIG_SITE_CHANGED, SIG_LOCATION_CHANGED, SIG_ROTATION_CHANGED, SIG_REFRESH, @@ -71,11 +71,6 @@ static void _gis_viewer_emit_time_changed(GisViewer *self) g_signal_emit(self, signals[SIG_TIME_CHANGED], 0, self->time); } -static void _gis_viewer_emit_site_changed(GisViewer *self) -{ - g_signal_emit(self, signals[SIG_SITE_CHANGED], 0, - self->site); -} static void _gis_viewer_emit_refresh(GisViewer *self) { g_signal_emit(self, signals[SIG_REFRESH], 0); @@ -89,12 +84,6 @@ static void _gis_viewer_emit_offline(GisViewer *self) /************* * Callbacks * *************/ -static gboolean on_button_press(GisViewer *self, GdkEventButton *event, gpointer _) -{ - g_debug("GisViewer: on_button_press - Grabbing focus"); - gtk_widget_grab_focus(GTK_WIDGET(self)); - return TRUE; -} static gboolean on_key_press(GisViewer *self, GdkEventKey *event, gpointer _) { g_debug("GisViewer: on_key_press - key=%x, state=%x, plus=%x", @@ -117,6 +106,59 @@ static gboolean on_key_press(GisViewer *self, GdkEventKey *event, gpointer _) else if (kv == GDK_L) gis_viewer_rotate(self, 0, 0, 2); return FALSE; } + +enum { + GIS_DRAG_NONE, + GIS_DRAG_PAN, + GIS_DRAG_ZOOM, + GIS_DRAG_TILT, +}; + +static gboolean on_button_press(GisViewer *self, GdkEventButton *event, gpointer _) +{ + g_debug("GisViewer: on_button_press - %d", event->button); + gtk_widget_grab_focus(GTK_WIDGET(self)); + switch (event->button) { + case 1: self->drag_mode = GIS_DRAG_PAN; break; + case 2: self->drag_mode = GIS_DRAG_ZOOM; break; + case 3: self->drag_mode = GIS_DRAG_TILT; break; + defualt: self->drag_mode = GIS_DRAG_NONE; break; + } + self->drag_x = event->x; + self->drag_y = event->y; + return FALSE; +} + +static gboolean on_button_release(GisViewer *self, GdkEventButton *event, gpointer _) +{ + g_debug("GisViewer: on_button_release"); + self->drag_mode = GIS_DRAG_NONE; + return FALSE; +} + +static gboolean on_motion_notify(GisViewer *self, GdkEventMotion *event, gpointer _) +{ + gdouble x_dist = self->drag_x - event->x; + gdouble y_dist = self->drag_y - event->y; + gdouble lat, lon, elev, scale; + gis_viewer_get_location(GIS_VIEWER(self), &lat, &lon, &elev); + scale = elev/EARTH_R/15; + switch (self->drag_mode) { + case GIS_DRAG_PAN: + gis_viewer_pan(self, -y_dist*scale, x_dist*scale, 0); + break; + case GIS_DRAG_ZOOM: + gis_viewer_zoom(self, pow(2, -y_dist/500)); + break; + case GIS_DRAG_TILT: + gis_viewer_rotate(self, y_dist/10, 0, x_dist/10); + break; + } + self->drag_x = event->x; + self->drag_y = event->y; + return FALSE; +} + static void on_view_changed(GisViewer *self, gdouble _1, gdouble _2, gdouble _3) { @@ -126,6 +168,13 @@ static void on_view_changed(GisViewer *self, /*********** * Methods * ***********/ +void gis_viewer_setup(GisViewer *self, GisPlugins *plugins, GisPrefs *prefs) +{ + self->plugins = plugins; + self->prefs = prefs; + self->offline = gis_prefs_get_boolean(prefs, "gis/offline", NULL); +} + void gis_viewer_set_time(GisViewer *self, const char *time) { g_assert(GIS_IS_VIEWER(self)); @@ -210,23 +259,6 @@ void gis_viewer_rotate(GisViewer *self, gdouble x, gdouble y, gdouble z) _gis_viewer_emit_rotation_changed(self); } -/* To be deprecated, use {get,set}_location */ -void gis_viewer_set_site(GisViewer *self, const gchar *site) -{ - g_assert(GIS_IS_VIEWER(self)); - g_debug("GisViewer: set_site"); - g_free(self->site); - self->site = g_strdup(site); - _gis_viewer_emit_site_changed(self); -} - -gchar *gis_viewer_get_site(GisViewer *self) -{ - g_assert(GIS_IS_VIEWER(self)); - g_debug("GisViewer: get_site - %s", self->site); - return self->site; -} - void gis_viewer_refresh(GisViewer *self) { g_debug("GisViewer: refresh"); @@ -237,6 +269,7 @@ void gis_viewer_set_offline(GisViewer *self, gboolean offline) { g_assert(GIS_IS_VIEWER(self)); g_debug("GisViewer: set_offline - %d", offline); + gis_prefs_set_boolean(self->prefs, "gis/offline", offline); self->offline = offline; _gis_viewer_emit_offline(self); } @@ -286,52 +319,21 @@ void gis_viewer_set_height_func(GisViewer *self, GisTile *tile, klass->set_height_func(self, tile, height_func, user_data, update); } -void gis_viewer_render_tile(GisViewer *self, GisTile *tile) -{ - GisViewerClass *klass = GIS_VIEWER_GET_CLASS(self); - if (!klass->render_tile) - g_warning("GisViewer: render_tile - Unimplemented"); - klass->render_tile(self, tile); -} - -void gis_viewer_render_tiles(GisViewer *self, GisTile *root) -{ - GisViewerClass *klass = GIS_VIEWER_GET_CLASS(self); - if (!klass->render_tiles) - g_warning("GisViewer: render_tiles - Unimplemented"); - klass->render_tiles(self, root); -} - -void gis_viewer_begin(GisViewer *self) -{ - GisViewerClass *klass = GIS_VIEWER_GET_CLASS(self); - if (!klass->begin) - g_warning("GisViewer: begin - Unimplemented"); - klass->begin(self); -} - -void gis_viewer_end(GisViewer *self) -{ - GisViewerClass *klass = GIS_VIEWER_GET_CLASS(self); - if (!klass->end) - g_warning("GisViewer: end - Unimplemented"); - klass->end(self); -} - -void gis_viewer_add(GisViewer *self, GisObject *object) +gpointer gis_viewer_add(GisViewer *self, GisObject *object, + gint level, gboolean sort) { GisViewerClass *klass = GIS_VIEWER_GET_CLASS(self); if (!klass->add) g_warning("GisViewer: add - Unimplemented"); - klass->add(self, object); + return klass->add(self, object, level, sort); } -void gis_viewer_remove(GisViewer *self, GisObject *object) +GisObject *gis_viewer_remove(GisViewer *self, gpointer ref) { GisViewerClass *klass = GIS_VIEWER_GET_CLASS(self); if (!klass->remove) g_warning("GisViewer: remove - Unimplemented"); - klass->remove(self, object); + return klass->remove(self, ref); } /**************** @@ -343,7 +345,6 @@ static void gis_viewer_init(GisViewer *self) g_debug("GisViewer: init"); /* Default values */ self->time = g_strdup(""); - self->site = g_strdup(""); self->location[0] = 40; self->location[1] = -100; self->location[2] = 1.5*EARTH_R; @@ -351,18 +352,27 @@ static void gis_viewer_init(GisViewer *self) self->rotation[1] = 0; self->rotation[2] = 0; - g_signal_connect(self, "key-press-event", G_CALLBACK(on_key_press), NULL); - g_signal_connect(self, "button-press-event", G_CALLBACK(on_button_press), NULL); + g_object_set(self, "can-focus", TRUE, NULL); + gtk_widget_add_events(GTK_WIDGET(self), + GDK_BUTTON_PRESS_MASK | + GDK_BUTTON_RELEASE_MASK | + GDK_POINTER_MOTION_MASK | + GDK_KEY_PRESS_MASK); - g_signal_connect(self, "location-changed", G_CALLBACK(on_view_changed), NULL); - g_signal_connect(self, "rotation-changed", G_CALLBACK(on_view_changed), NULL); + g_signal_connect(self, "key-press-event", G_CALLBACK(on_key_press), NULL); + + g_signal_connect(self, "button-press-event", G_CALLBACK(on_button_press), NULL); + g_signal_connect(self, "button-release-event", G_CALLBACK(on_button_release), NULL); + g_signal_connect(self, "motion-notify-event", G_CALLBACK(on_motion_notify), NULL); + + g_signal_connect(self, "location-changed", G_CALLBACK(on_view_changed), NULL); + g_signal_connect(self, "rotation-changed", G_CALLBACK(on_view_changed), NULL); } static void gis_viewer_finalize(GObject *gobject) { g_debug("GisViewer: finalize"); GisViewer *self = GIS_VIEWER(gobject); g_free(self->time); - g_free(self->site); G_OBJECT_CLASS(gis_viewer_parent_class)->finalize(gobject); } static void gis_viewer_class_init(GisViewerClass *klass) @@ -381,17 +391,6 @@ static void gis_viewer_class_init(GisViewerClass *klass) G_TYPE_NONE, 1, G_TYPE_STRING); - signals[SIG_SITE_CHANGED] = g_signal_new( - "site-changed", - G_TYPE_FROM_CLASS(gobject_class), - G_SIGNAL_RUN_LAST, - 0, - NULL, - NULL, - g_cclosure_marshal_VOID__STRING, - G_TYPE_NONE, - 1, - G_TYPE_STRING); signals[SIG_LOCATION_CHANGED] = g_signal_new( "location-changed", G_TYPE_FROM_CLASS(gobject_class),