From 55d69c616a9f4f3bae23045f1174047003e2e1d4 Mon Sep 17 00:00:00 2001 From: Andy Spencer Date: Sun, 24 May 2009 06:55:40 +0000 Subject: [PATCH] Example plugin in GObject plugin format --- src/Makefile.am | 19 +++---- src/aweather-gui.c | 115 +++++++++++++++++++++++------------------- src/aweather-gui.h | 5 +- src/aweather-plugin.c | 32 ++++++++++++ src/aweather-plugin.h | 26 ++++++++++ src/aweather-view.c | 12 +++-- src/location.h | 4 +- src/main.c | 6 ++- src/plugin-example.c | 111 +++++++++++++++++++++++++--------------- src/plugin-example.h | 34 +++++++++++-- src/plugin-radar.h | 4 +- src/plugin-ridge.h | 4 +- 12 files changed, 253 insertions(+), 119 deletions(-) diff --git a/src/Makefile.am b/src/Makefile.am index fad1033..705df0e 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -5,15 +5,16 @@ bin_PROGRAMS = aweather wsr88ddec BUILT_SOURCES = marshal.c marshal.h aweather_SOURCES = main.c \ - marshal.c marshal.h \ - aweather-gui.c aweather-gui.h \ - aweather-view.c aweather-view.h \ - data.c data.h \ - location.c location.h \ - plugin-radar.c plugin-radar.h \ - plugin-radar-colormap.c \ - plugin-ridge.c plugin-ridge.h \ - plugin-example.c plugin-example.h + marshal.c marshal.h \ + aweather-gui.c aweather-gui.h \ + aweather-view.c aweather-view.h \ + aweather-plugin.c aweather-plugin.h \ + data.c data.h \ + location.c location.h \ + plugin-radar.c plugin-radar.h \ + plugin-radar-colormap.c \ + plugin-ridge.c plugin-ridge.h \ + plugin-example.c plugin-example.h aweather_CPPFLAGS = $(RSL_CFLAGS) $(GTK_CFLAGS) -DDATADIR="\"$(datadir)\"" wsr88ddec = wsr88ddec.c diff --git a/src/aweather-gui.c b/src/aweather-gui.c index 02b33e1..7adecf0 100644 --- a/src/aweather-gui.c +++ b/src/aweather-gui.c @@ -25,10 +25,52 @@ #include "aweather-gui.h" #include "aweather-view.h" +#include "aweather-plugin.h" #include "location.h" +/**************** + * GObject code * + ****************/ +G_DEFINE_TYPE(AWeatherGui, aweather_gui, G_TYPE_OBJECT); +static void aweather_gui_init(AWeatherGui *gui) +{ + gui->plugins = NULL; + //g_message("aweather_gui_init"); +} +static GObject *aweather_gui_constructor(GType gtype, guint n_properties, + GObjectConstructParam *properties) +{ + //g_message("aweather_gui_constructor"); + GObjectClass *parent_class = G_OBJECT_CLASS(aweather_gui_parent_class); + return parent_class->constructor(gtype, n_properties, properties); +} +static void aweather_gui_dispose (GObject *gobject) +{ + //g_message("aweather_gui_dispose"); + AWeatherGui *gui = AWEATHER_GUI(gobject); + g_object_unref(gui->view ); + g_object_unref(gui->builder); + g_object_unref(gui->window ); + g_object_unref(gui->tabs ); + g_object_unref(gui->drawing); + G_OBJECT_CLASS(aweather_gui_parent_class)->dispose(gobject); +} +static void aweather_gui_finalize(GObject *gobject) +{ + //g_message("aweather_gui_finalize"); + G_OBJECT_CLASS(aweather_gui_parent_class)->finalize(gobject); +} +static void aweather_gui_class_init(AWeatherGuiClass *klass) +{ + //g_message("aweather_gui_class_init"); + GObjectClass *gobject_class = G_OBJECT_CLASS(klass); + gobject_class->constructor = aweather_gui_constructor; + gobject_class->dispose = aweather_gui_dispose; + gobject_class->finalize = aweather_gui_finalize; +} + /************* - * callbacks * + * Callbacks * *************/ gboolean on_key_press(GtkWidget *widget, GdkEventKey *event, AWeatherGui *gui) { @@ -148,8 +190,8 @@ gboolean on_configure(GtkWidget *da, GdkEventConfigure *event, AWeatherGui *gui) double rad = atan((height/2)/500); double deg = (rad*180)/M_PI; - /* TODO: set clipping plane properly */ - gluPerspective(deg*2, width/height, -z-20, -z+20); + //gluPerspective(deg*2, width/height, -z-20, -z+20); + gluPerspective(deg*2, width/height, 1, 500*1000); aweather_gui_gl_end(gui); return FALSE; @@ -157,7 +199,7 @@ gboolean on_configure(GtkWidget *da, GdkEventConfigure *event, AWeatherGui *gui) gboolean on_expose_begin(GtkWidget *da, GdkEventExpose *event, AWeatherGui *gui) { - g_message("aweather:espose_begin"); + g_message("aweather:expose_begin"); aweather_gui_gl_begin(gui); double x, y, z; @@ -170,11 +212,17 @@ gboolean on_expose_begin(GtkWidget *da, GdkEventExpose *event, AWeatherGui *gui) //glRotatef(-45, 1, 0, 0); + /* Expose plugins */ + for (GList *cur = gui->plugins; cur; cur = cur->next) { + AWeatherPlugin *plugin = AWEATHER_PLUGIN(cur->data); + aweather_plugin_expose(plugin); + } + return FALSE; } gboolean on_expose_end(GtkWidget *da, GdkEventExpose *event, AWeatherGui *gui) { - g_message("aweather:espose_end\n"); + g_message("aweather:expose_end\n"); aweather_gui_gl_end(gui); aweather_gui_gl_flush(gui); return FALSE; @@ -331,53 +379,10 @@ static void opengl_setup(AWeatherGui *gui) } -/**************** - * GObject code * - ****************/ -G_DEFINE_TYPE(AWeatherGui, aweather_gui, G_TYPE_OBJECT); - -/* Constructor / destructors */ -static void aweather_gui_init(AWeatherGui *gui) -{ - //g_message("aweather_gui_init"); -} - -static GObject *aweather_gui_constructor(GType gtype, guint n_properties, - GObjectConstructParam *properties) -{ - //g_message("aweather_gui_constructor"); - GObjectClass *parent_class = G_OBJECT_CLASS(aweather_gui_parent_class); - return parent_class->constructor(gtype, n_properties, properties); -} - -static void aweather_gui_dispose (GObject *gobject) -{ - //g_message("aweather_gui_dispose"); - AWeatherGui *gui = AWEATHER_GUI(gobject); - g_object_unref(gui->view ); - g_object_unref(gui->builder); - g_object_unref(gui->window ); - g_object_unref(gui->tabs ); - g_object_unref(gui->drawing); - G_OBJECT_CLASS(aweather_gui_parent_class)->dispose(gobject); -} - -static void aweather_gui_finalize(GObject *gobject) -{ - //g_message("aweather_gui_finalize"); - G_OBJECT_CLASS(aweather_gui_parent_class)->finalize(gobject); -} - -static void aweather_gui_class_init(AWeatherGuiClass *klass) -{ - //g_message("aweather_gui_class_init"); - GObjectClass *gobject_class = G_OBJECT_CLASS(klass); - gobject_class->constructor = aweather_gui_constructor; - gobject_class->dispose = aweather_gui_dispose; - gobject_class->finalize = aweather_gui_finalize; -} -/* Methods */ +/*********** + * Methods * + ***********/ AWeatherGui *aweather_gui_new() { //g_message("aweather_gui_new"); @@ -396,7 +401,7 @@ AWeatherGui *aweather_gui_new() /* Load components */ - aweather_view_set_location(gui->view, 0, 0, -500*1000); + aweather_view_set_location(gui->view, 0, 0, -300*1000); g_signal_connect(gui->view, "location-changed", G_CALLBACK(on_location_changed), gui); site_setup(gui); time_setup(gui); @@ -421,6 +426,11 @@ GtkWidget *aweather_gui_get_widget(AWeatherGui *gui, const gchar *name) g_error("Failed to get widget `%s'", name); return GTK_WIDGET(widget); } +void aweather_gui_register_plugin(AWeatherGui *gui, AWeatherPlugin *plugin) +{ + g_message("registering plugin"); + gui->plugins = g_list_append(gui->plugins, plugin); +} void aweather_gui_gl_redraw(AWeatherGui *gui) { g_message("redraw"); @@ -456,4 +466,3 @@ void aweather_gui_gl_flush(AWeatherGui *gui) glFlush(); gdk_gl_drawable_gl_end(gldrawable); } -//void aweather_gui_register_plugin(AWeatherGui *gui, AWeatherPlugin *plugin); diff --git a/src/aweather-gui.h b/src/aweather-gui.h index 70e03a6..91e53d2 100644 --- a/src/aweather-gui.h +++ b/src/aweather-gui.h @@ -21,6 +21,7 @@ #include #include #include "aweather-view.h" +#include "aweather-plugin.h" /* Type macros */ #define AWEATHER_TYPE_GUI (aweather_gui_get_type()) @@ -42,6 +43,7 @@ struct _AWeatherGui { GtkWindow *window; GtkNotebook *tabs; GtkDrawingArea *drawing; + GList *plugins; }; struct _AWeatherGuiClass { @@ -56,11 +58,10 @@ GType aweather_gui_get_type(void); AWeatherGui *aweather_gui_new(); AWeatherView *aweather_gui_get_view(AWeatherGui *gui); GtkWidget *aweather_gui_get_widget(AWeatherGui *gui, const gchar *name); +void aweather_gui_register_plugin(AWeatherGui *gui, AWeatherPlugin *plugin); void aweather_gui_gl_redraw(AWeatherGui *gui); void aweather_gui_gl_begin(AWeatherGui *gui); void aweather_gui_gl_end(AWeatherGui *gui); void aweather_gui_gl_flush(AWeatherGui *gui); -//void aweather_gui_register_plugin(AWeatherGui *gui, AWeatherPlugin *plugin); - #endif diff --git a/src/aweather-plugin.c b/src/aweather-plugin.c index 8546f76..87cf35c 100644 --- a/src/aweather-plugin.c +++ b/src/aweather-plugin.c @@ -15,4 +15,36 @@ * along with this program. If not, see . */ +#include +#include "aweather-plugin.h" + +static void aweather_plugin_base_init(gpointer g_class) +{ + static gboolean is_initialized = FALSE; + if (!is_initialized) { + /* add properties and signals to the interface here */ + is_initialized = TRUE; + } +} + +GType aweather_plugin_get_type() +{ + static GType type = 0; + if (type == 0) { + static const GTypeInfo info = { + sizeof(AWeatherPluginInterface), + aweather_plugin_base_init, + NULL, + }; + type = g_type_register_static(G_TYPE_INTERFACE, + "AWeatherPlugin", &info, 0); + } + return type; +} + +void aweather_plugin_expose(AWeatherPlugin *self) +{ + g_return_if_fail(AWEATHER_IS_PLUGIN(self)); + AWEATHER_PLUGIN_GET_INTERFACE(self)->expose(self); +} diff --git a/src/aweather-plugin.h b/src/aweather-plugin.h index 8546f76..7112e64 100644 --- a/src/aweather-plugin.h +++ b/src/aweather-plugin.h @@ -15,4 +15,30 @@ * along with this program. If not, see . */ +#ifndef __AWEATHER_PLUGIN_H__ +#define __AWEATHER_PLUGIN_H__ +#include + +#define AWEATHER_TYPE_PLUGIN (aweather_plugin_get_type()) +#define AWEATHER_PLUGIN(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), AWEATHER_TYPE_PLUGIN, AWeatherPlugin)) +#define AWEATHER_IS_PLUGIN(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), AWEATHER_TYPE_PLUGIN)) +#define AWEATHER_PLUGIN_GET_INTERFACE(inst) (G_TYPE_INSTANCE_GET_INTERFACE((inst), AWEATHER_TYPE_PLUGIN, AWeatherPluginInterface)) + + +typedef struct _AWeatherPlugin AWeatherPlugin; +typedef struct _AWeatherPluginInterface AWeatherPluginInterface; + +struct _AWeatherPluginInterface +{ + GTypeInterface parent_iface; + + /* Virtual functions */ + void (*expose)(AWeatherPlugin *self); +}; + +GType aweather_plugin_get_type(void); + +void aweather_plugin_expose(AWeatherPlugin *self); + +#endif diff --git a/src/aweather-view.c b/src/aweather-view.c index 8b7eade..7caaf9b 100644 --- a/src/aweather-view.c +++ b/src/aweather-view.c @@ -20,6 +20,9 @@ #include "marshal.h" #include "aweather-view.h" +/**************** + * GObject code * + ****************/ G_DEFINE_TYPE(AWeatherView, aweather_view, G_TYPE_OBJECT); enum { @@ -38,13 +41,12 @@ enum { static guint signals[NUM_SIGNALS]; -/* Constructor / destructors */ static void aweather_view_init(AWeatherView *self) { //g_message("aweather_view_init"); /* Default values */ - self->time = g_strdup(""); //g_strdup("LATEST"); - self->site = g_strdup(""); //g_strdup("IND"); + self->time = g_strdup(""); + self->site = g_strdup(""); } static GObject *aweather_view_constructor(GType gtype, guint n_properties, @@ -187,7 +189,9 @@ static void _aweather_view_emit_refresh(AWeatherView *view) } -/* Methods */ +/*********** + * Methods * + ***********/ AWeatherView *aweather_view_new() { //g_message("aweather_view_new"); diff --git a/src/location.h b/src/location.h index e105de8..82cf38c 100644 --- a/src/location.h +++ b/src/location.h @@ -15,8 +15,8 @@ * along with this program. If not, see . */ -#ifndef SITE_H -#define SITE_H +#ifndef __SITE_H__ +#define __SITE_H__ enum { LOCATION_CITY, diff --git a/src/main.c b/src/main.c index cf13c87..773b033 100644 --- a/src/main.c +++ b/src/main.c @@ -38,8 +38,10 @@ int main(int argc, char *argv[]) /* Load plugins */ //example_init(gui); - ridge_init(gui); - radar_init(gui); + //ridge_init(gui); + //radar_init(gui); + + aweather_gui_register_plugin(gui, AWEATHER_PLUGIN(aweather_example_new(gui))); gtk_widget_show_all(aweather_gui_get_widget(gui, "window")); gtk_main(); diff --git a/src/plugin-example.c b/src/plugin-example.c index 8b6361d..553dd3d 100644 --- a/src/plugin-example.c +++ b/src/plugin-example.c @@ -21,23 +21,83 @@ #include #include "aweather-gui.h" +#include "aweather-plugin.h" +#include "plugin-example.h" + +/**************** + * GObject code * + ****************/ +static void aweather_example_plugin_init(AWeatherPluginInterface *iface); +static void aweather_example_expose(AWeatherPlugin *_example); +G_DEFINE_TYPE_WITH_CODE(AWeatherExample, aweather_example, G_TYPE_OBJECT, + G_IMPLEMENT_INTERFACE(AWEATHER_TYPE_PLUGIN, + aweather_example_plugin_init)); +static void aweather_example_class_init(AWeatherExampleClass *klass) +{ + GObjectClass *object_class = (GObjectClass*)klass; +} +static void aweather_example_plugin_init(AWeatherPluginInterface *iface) +{ + /* Add methods to the interface */ + iface->expose = aweather_example_expose; +} +static void aweather_example_init(AWeatherExample *example) +{ + /* Set defaults */ + example->gui = NULL; + example->button = NULL; + example->rotation = 30.0; +} + +/*********** + * Helpers * + ***********/ +static gboolean rotate(gpointer _example) +{ + AWeatherExample *example = _example; + if (gtk_toggle_button_get_active(example->button)) { + example->rotation += 1.0; + aweather_gui_gl_redraw(example->gui); + } + return TRUE; +} + +/*********** + * Methods * + ***********/ +AWeatherExample *aweather_example_new(AWeatherGui *gui) +{ + //g_message("aweather_view_new"); + AWeatherExample *example = g_object_new(AWEATHER_TYPE_EXAMPLE, NULL); + example->gui = gui; -static GtkWidget *rotate_button; + GtkWidget *drawing = aweather_gui_get_widget(gui, "drawing"); + GtkWidget *config = aweather_gui_get_widget(gui, "tabs"); -static float ang = 30.; + /* Add configuration tab */ + GtkWidget *label = gtk_label_new("example"); + example->button = GTK_TOGGLE_BUTTON(gtk_toggle_button_new_with_label("Rotate")); + gtk_notebook_append_page(GTK_NOTEBOOK(config), GTK_WIDGET(example->button), label); -static gboolean expose(GtkWidget *da, GdkEventExpose *event, gpointer user_data) + /* Set up OpenGL Stuff */ + //g_signal_connect(drawing, "expose-event", G_CALLBACK(expose), NULL); + g_timeout_add(1000/60, rotate, example); + + return example; +} + +static void aweather_example_expose(AWeatherPlugin *_example) { + AWeatherExample *example = AWEATHER_EXAMPLE(_example); + g_message("aweather_example_expose"); glDisable(GL_TEXTURE_2D); - glMatrixMode(GL_MODELVIEW ); glPushMatrix(); glLoadIdentity(); glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity(); - //glOrtho(-1,1,-1,1,-10,10); - - glTranslatef(0.5, -0.5, -2); + glOrtho(-1,1,-1,1,-10,10); + glMatrixMode(GL_MODELVIEW ); glPushMatrix(); glLoadIdentity(); float light_ambient[] = {0.1f, 0.1f, 0.0f}; float light_diffuse[] = {0.9f, 0.9f, 0.9f}; - float light_position[] = {-20.0f, 40.0f, -40.0f, 1.0f}; + float light_position[] = {-30.0f, 50.0f, 40.0f, 1.0f}; glLightfv(GL_LIGHT0, GL_AMBIENT, light_ambient); glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse); glLightfv(GL_LIGHT0, GL_POSITION, light_position); @@ -45,7 +105,8 @@ static gboolean expose(GtkWidget *da, GdkEventExpose *event, gpointer user_data) glEnable(GL_LIGHTING); glEnable(GL_COLOR_MATERIAL); - glRotatef(ang, 1, 0, 1); + glTranslatef(0.5, -0.5, -2); + glRotatef(example->rotation, 1, 0, 1); glColor4f(0.9, 0.9, 0.7, 1.0); gdk_gl_draw_teapot(TRUE, 0.25); gdk_gl_draw_cube(TRUE, 0.25); @@ -57,36 +118,6 @@ static gboolean expose(GtkWidget *da, GdkEventExpose *event, gpointer user_data) glMatrixMode(GL_PROJECTION); glPopMatrix(); glMatrixMode(GL_MODELVIEW ); glPopMatrix(); - return FALSE; -} - -static gboolean rotate(gpointer user_data) -{ - if (!gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(rotate_button))) - return TRUE; - - GtkWidget *da = GTK_WIDGET (user_data); - - ang++; - - gdk_window_invalidate_rect(da->window, &da->allocation, FALSE); - gdk_window_process_updates(da->window, FALSE); - - return TRUE; + return; } -gboolean example_init(AWeatherGui *gui) -{ - GtkWidget *drawing = aweather_gui_get_widget(gui, "drawing"); - GtkWidget *config = aweather_gui_get_widget(gui, "tabs"); - - /* Add configuration tab */ - GtkWidget *label = gtk_label_new("example"); - rotate_button = gtk_toggle_button_new_with_label("Rotate"); - gtk_notebook_append_page(GTK_NOTEBOOK(config), rotate_button, label); - - /* Set up OpenGL Stuff */ - g_signal_connect(drawing, "expose-event", G_CALLBACK(expose), NULL); - g_timeout_add(1000/60, rotate, drawing); - return TRUE; -} diff --git a/src/plugin-example.h b/src/plugin-example.h index 66c1cbf..5e52f6e 100644 --- a/src/plugin-example.h +++ b/src/plugin-example.h @@ -15,9 +15,37 @@ * along with this program. If not, see . */ -#ifndef EXAMPLE_H -#define EXAMPLE_H +#ifndef __EXAMPLE_H__ +#define __EXAMPLE_H__ -gboolean example_init(AWeatherGui *gui); +#include + +#define AWEATHER_TYPE_EXAMPLE (aweather_example_get_type ()) +#define AWEATHER_EXAMPLE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), AWEATHER_TYPE_EXAMPLE, AWeatherExample)) +#define AWEATHER_IS_EXAMPLE(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), AWEATHER_TYPE_EXAMPLE)) +#define AWEATHER_EXAMPLE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), AWEATHER_TYPE_EXAMPLE, AWeatherExampleClass)) +#define AWEATHER_IS_EXAMPLE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), AWEATHER_TYPE_EXAMPLE)) +#define AWEATHER_EXAMPLE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), AWEATHER_TYPE_EXAMPLE, AWeatherExampleClass)) + +typedef struct _AWeatherExample AWeatherExample; +typedef struct _AWeatherExampleClass AWeatherExampleClass; + +struct _AWeatherExample { + GObject parent_instance; + + /* instance members */ + AWeatherGui *gui; + GtkToggleButton *button; + float rotation; +}; + +struct _AWeatherExampleClass { + GObjectClass parent_class; +}; + +GType aweather_example_get_type (void); + +/* Methods */ +AWeatherExample *aweather_example_new(AWeatherGui *gui); #endif diff --git a/src/plugin-radar.h b/src/plugin-radar.h index 7b787d8..2bc422a 100644 --- a/src/plugin-radar.h +++ b/src/plugin-radar.h @@ -15,8 +15,8 @@ * along with this program. If not, see . */ -#ifndef RADAR_H -#define RADAR_H +#ifndef __RADAR_H__ +#define __RADAR_H__ gboolean radar_init(AWeatherGui *gui); diff --git a/src/plugin-ridge.h b/src/plugin-ridge.h index 00fed65..9d5ca04 100644 --- a/src/plugin-ridge.h +++ b/src/plugin-ridge.h @@ -15,8 +15,8 @@ * along with this program. If not, see . */ -#ifndef RIDGE_H -#define RIDGE_H +#ifndef __RIDGE_H__ +#define __RIDGE_H__ gboolean ridge_init(AWeatherGui *gui); -- 2.43.2