diff plugins/crazychat/cc_gaim_plugin.c @ 11232:8bcd4d4ccef6

[gaim-migrate @ 13372] committing crazychat again. hopefully here to stay. committer: Tailor Script <tailor@pidgin.im>
author Charlie Stockman <chuckleberry>
date Thu, 11 Aug 2005 07:56:29 +0000
parents
children f09c6e8df82c
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/plugins/crazychat/cc_gaim_plugin.c	Thu Aug 11 07:56:29 2005 +0000
@@ -0,0 +1,485 @@
+#include <stdio.h>
+#include <assert.h>
+
+#include "internal.h"
+#include "plugin.h"
+#include "gtkplugin.h"
+#include "gtkblist.h"
+#include "gtkutils.h"
+#include "connection.h"
+#include "conversation.h"
+#include "network.h"
+
+#include <gtk/gtkgl.h>
+#include <GL/gl.h>
+#include <GL/glu.h>
+
+#include "crazychat.h"
+#include "cc_network.h"
+#include "cc_interface.h"
+#include "cc_gtk_gl.h"
+#include "util.h"
+
+/* --- begin type and global variable definitions --- */
+
+static struct crazychat cc_info;
+
+/* --- begin function declarations --- */
+
+/**
+ * Called by gaim plugin to start CrazyChat
+ * @param cc	the crazychat struct
+ */
+static void cc_init(struct crazychat *cc);
+
+/**
+ * Called by gaim plugin to destroy CrazyChat
+ * @param cc	the crazychat struct
+ */
+static void cc_destroy(struct crazychat *cc);
+
+
+/**
+ * Buddy menu drawing callback.  Adds a CrazyChat menuitem.
+ * @param menu	the buddy menu widget
+ * @param b	the buddy whose menu this is
+ */
+static gboolean cc_buddy_menu(GtkWidget *menu, GaimBuddy *b);
+
+/**
+ * Buddy menu callback.  Initiates the CrazyChat session.
+ * @param item	the gtk buddy menu item
+ * @param b	the buddy whose menu the item was in
+ */
+static void cc_menu_cb(GtkMenuItem *item, GaimBuddy *b);
+
+/**
+ * IM callback.  Handles receiving a CrazyChat session request.
+ * @param account	the account we received the IM on
+ * @param sender	the buddy who we received the message from
+ * @param message	the message we received
+ * @param flags		IM flags
+ * @param data		user data
+ */
+static gboolean receive_im_cb(GaimAccount *account, char **sender,
+		char **message,	int *flags, void *data);
+
+/**
+ * Displaying IM callback.  Drops CrazyChat messages from IM window.
+ * @param account	the account we are displaying the IM on
+ * @param conv		the conversation we are displaying the IM on
+ * @param message	the message we are displaying
+ * @param data		user data
+ */
+static gboolean display_im_cb(GaimAccount *account, GaimConversation *conv,
+		char **message, void *data);
+
+/**
+ * Callback for CrazyChat plugin configuration frame
+ * @param plugin	the plugin data
+ * @return	the configuration frame
+ */
+static GtkWidget *get_config_frame(GaimPlugin *plugin);
+
+/**
+ * TCP port callback.  Changes the port used to listen for new CC sessions
+ * @param spin		the spinner button whose value changed
+ * @param data		user data
+ */
+static void tcp_port_cb(GtkSpinButton *spin, struct crazychat *cc);
+
+/**
+ * UDP port callback.  Changes the port used to send/recv CC session frames
+ * @param spin		the spinner button whose value changed
+ * @param data		user data
+ */
+static void udp_port_cb(GtkSpinButton *spin, struct crazychat *cc);
+
+/**
+ * Features enabling/disabling callback.  Initializes the input processing
+ * or shuts it down.
+ * @param data		user data
+ */
+static void features_enable_cb(struct crazychat *cc);
+
+/**
+ * User signed on callback.  Now we have a buddy list to connect a signal
+ * handler to.
+ * @param gc		the gaim connection we are signed on
+ * @param plugin	our plugin struct
+ */
+static gboolean cc_signed_on(GaimConnection *gc, void *plugin);
+
+/**
+ * Plugin loading callback.  If a buddy list exists, connect our buddy menu
+ * drawing callback to the signal handler, otherwise, connect a signed on
+ * signal handler so we know when we get a buddy list.
+ * @param plugin	our plugin struct
+ */
+static gboolean plugin_load(GaimPlugin *plugin);
+
+/**
+ * Plugin unloading callback.  Disconnect all handlers and free data.
+ * @param plugin	our plugin struct
+ */
+static gboolean plugin_unload(GaimPlugin *plugin);
+
+
+/* --- end function declarations --- */
+
+
+#define CRAZYCHAT_PLUGIN_ID "gtk-crazychat"
+
+static GaimGtkPluginUiInfo ui_info = {
+	get_config_frame				/**< get_config_frame */
+};
+
+static GaimPluginInfo info = {
+	2,						  /**< api_version    */
+	GAIM_PLUGIN_STANDARD,				  /**< type           */
+	GAIM_GTK_PLUGIN_TYPE,				  /**< ui_requirement */
+	0,						  /**< flags          */
+	NULL,						  /**< dependencies   */
+	GAIM_PRIORITY_DEFAULT,				  /**< priority       */
+
+	CRAZYCHAT_PLUGIN_ID,				  /**< id             */
+	N_("Crazychat"),				  /**< name           */
+	VERSION,					  /**< version        */
+							  /**  summary        */
+	N_("Plugin to establish a Crazychat session."),
+							  /**  description    */
+	N_("Uses Gaim to obtain buddy ips to connect for a Crazychat session"),
+	"\n"
+	"William Chan <chanman@stanford.edu>\n"
+	"Ian Spiro <ispiro@stanford.edu>\n"
+	"Charlie Stockman<stockman@stanford.edu>\n"
+	"Steve Yelderman<scy@stanford.edu>",		  /**< author         */
+	GAIM_WEBSITE,					  /**< homepage       */
+
+	plugin_load,					  /**< load           */
+	plugin_unload,					  /**< unload         */
+	NULL,						  /**< destroy        */
+
+	&ui_info,					  /**< ui_info        */
+	&cc_info					  /**< extra_info     */
+};
+
+/* --- end plugin struct definition --- */
+
+static void cc_init(struct crazychat *cc)
+{
+	/* initialize main crazychat thread */
+	
+	assert(cc);
+	memset(cc, 0, sizeof(*cc));
+
+	/* initialize network configuration */
+	cc->tcp_port = DEFAULT_CC_PORT;
+	cc->udp_port = DEFAULT_CC_PORT;
+
+	/* disable input subsystem */
+	//cc->features_state = 0;
+
+	/* initialize input subsystem */
+	cc->features_state = 1;
+	cc->input_data = init_input(cc);
+}
+
+static void cc_destroy(struct crazychat *cc)
+{
+	assert(cc);
+
+	if (cc->features_state) {
+		destroy_input(cc->input_data);
+	}
+	memset(cc, 0, sizeof(*cc));
+}
+
+static gboolean cc_buddy_menu(GtkWidget *menu, GaimBuddy *b)
+{
+	GtkWidget *menuitem;
+
+	menuitem = gtk_menu_item_new_with_mnemonic("CrazyChat");
+	g_signal_connect(G_OBJECT(menuitem), "activate",
+			G_CALLBACK(cc_menu_cb), b);
+	gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem);
+	return FALSE;
+}
+
+static void cc_menu_cb(GtkMenuItem *item, GaimBuddy *b)
+{
+	assert(item);
+	assert(b);
+
+	/* send the invite */
+	cc_net_send_invite(&cc_info, b->name, b->account);
+}
+
+static gboolean receive_im_cb(GaimAccount *account, char **sender,
+		char **message,	int *flags, void *data)
+{
+	struct crazychat *cc;
+
+	cc = (struct crazychat*)data;
+	assert(cc);
+	if (!strncmp(*message, CRAZYCHAT_INVITE_CODE,
+				strlen(CRAZYCHAT_INVITE_CODE))) {
+		Debug(*message);
+		char *split = strchr(*message, '!');
+		assert(split);
+		*split = 0;
+		split++;
+		cc_net_recv_invite(account, cc, *sender,
+				&(*message)[strlen(CRAZYCHAT_INVITE_CODE)],
+				split);
+		return TRUE;
+	} else if (!strncmp(*message, CRAZYCHAT_ACCEPT_CODE,
+				strlen(CRAZYCHAT_ACCEPT_CODE))) {
+		cc_net_recv_accept(account, cc, *sender,
+				&(*message)[strlen(CRAZYCHAT_ACCEPT_CODE)]);
+		return TRUE;
+	} else if (!strncmp(*message, CRAZYCHAT_READY_CODE,
+				strlen(CRAZYCHAT_READY_CODE))) {
+		cc_net_recv_ready(account, cc, *sender);
+		return TRUE;
+	}
+	
+	return FALSE;
+}
+
+static gboolean display_im_cb(GaimAccount *account, GaimConversation *conv,
+		char **message, void *data)
+{
+	struct crazychat *cc;
+
+	cc = (struct crazychat*)data;
+	assert(cc);
+	if (!strncmp(*message, CRAZYCHAT_INVITE_CODE,
+				strlen(CRAZYCHAT_INVITE_CODE))) {
+		return TRUE;
+	} else if (!strncmp(*message, CRAZYCHAT_ACCEPT_CODE,
+				strlen(CRAZYCHAT_ACCEPT_CODE))) {
+		return TRUE;
+	} else if (!strncmp(*message, CRAZYCHAT_READY_CODE,
+				strlen(CRAZYCHAT_READY_CODE))) {
+		return TRUE;
+	}
+
+	return FALSE;
+}
+
+static GtkWidget *get_config_frame(GaimPlugin *plugin)
+{
+	GtkWidget *ret;
+	GtkWidget *frame;
+	GtkWidget *vbox, *hbox;
+	GtkWidget *drawing_area;
+	GtkWidget *label;
+	GtkAdjustment *adj;
+	GtkWidget *spinner;
+	GtkWidget *button, *button1, *button2;
+	GSList *group;
+	struct draw_info *info;
+	struct crazychat *cc;
+
+	cc = (struct crazychat*)plugin->info->extra_info;
+	assert(cc);
+
+	/* create widgets */
+
+	/* creating the config frame */
+	ret = gtk_vbox_new(FALSE, 18);
+	gtk_container_set_border_width(GTK_CONTAINER(ret), 12);
+
+	/* make the network configuration frame */
+	frame = gaim_gtk_make_frame(ret, _("Network Configuration"));
+	gtk_widget_show(frame);
+
+	/* add boxes for packing purposes */
+	vbox = gtk_vbox_new(FALSE, 0);
+	gtk_box_pack_start(GTK_BOX(frame), vbox, TRUE, TRUE, 0);
+	gtk_widget_show(vbox);
+
+	/* add widgets to row 1 */
+	hbox = gtk_hbox_new(FALSE, 0);
+	gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
+	gtk_widget_show(hbox);
+	label = gtk_label_new(_("TCP port"));
+	gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 15);
+	gtk_widget_show(label);
+	adj = (GtkAdjustment*)gtk_adjustment_new(DEFAULT_CC_PORT, 1,
+			G_MAXUSHORT, 1, 1000, 0);
+	spinner = gtk_spin_button_new(adj, 1, 0);
+	g_signal_connect(G_OBJECT(spinner), "value_changed",
+			G_CALLBACK(tcp_port_cb), cc);
+	gtk_box_pack_start(GTK_BOX(hbox), spinner, FALSE, FALSE, 0);
+	gtk_widget_show(spinner);
+	label = gtk_label_new(_("UDP port"));
+	gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 15);
+	gtk_widget_show(label);
+	adj = (GtkAdjustment*)gtk_adjustment_new(DEFAULT_CC_PORT, 1,
+			G_MAXUSHORT, 1, 1000, 0);
+	spinner = gtk_spin_button_new(adj, 1, 0);
+	g_signal_connect(G_OBJECT(spinner), "value_changed",
+			G_CALLBACK(udp_port_cb), cc);
+	gtk_box_pack_start(GTK_BOX(hbox), spinner, FALSE, FALSE, 0);
+	gtk_widget_show(spinner);
+
+	/* make the feature configuration frame */
+	frame = gaim_gtk_make_frame(ret, _("Feature Calibration"));
+	gtk_widget_show(frame);
+
+	/* add hbox for packing purposes */
+	hbox = gtk_hbox_new(TRUE, 40);
+	gtk_box_pack_start(GTK_BOX(frame), hbox, TRUE, TRUE, 0);
+	gtk_widget_show(hbox);
+
+	/* add feature calibration options */
+
+	/* add vbox for packing purposes */
+	vbox = gtk_vbox_new(TRUE, 0);
+	gtk_box_pack_start(GTK_BOX(hbox), vbox, TRUE, TRUE, 0);
+	gtk_widget_show(vbox);
+
+	/* add enabled / disabled */
+	button1 = gtk_radio_button_new_with_label(NULL, _("Enabled"));
+	gtk_box_pack_start(GTK_BOX(vbox), button1, TRUE, TRUE, 0);
+	gtk_widget_show(button1);
+	
+	group = gtk_radio_button_get_group(GTK_RADIO_BUTTON(button1));
+	button2 = gtk_radio_button_new_with_label(group, _("Disabled"));
+	gtk_box_pack_start(GTK_BOX(vbox), button2, TRUE, TRUE, 0);
+	gtk_widget_show(button2);
+
+	gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button1),
+			cc->features_state);
+	gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button2),
+			!cc->features_state);
+	g_signal_connect_swapped(G_OBJECT(button1), "toggled",
+			G_CALLBACK(features_enable_cb), cc);
+
+	/* add vbox for packing purposes */
+	vbox = gtk_vbox_new(TRUE, 0);
+	gtk_box_pack_end(GTK_BOX(hbox), vbox, TRUE, TRUE, 0);
+	gtk_widget_show(vbox);
+
+	/* add calibrate button */
+	button = gtk_button_new_with_label("Calibrate");
+	gtk_box_pack_start(GTK_BOX(vbox), button, TRUE, FALSE, 0);
+	gtk_widget_show(button);
+	
+	gtk_widget_show(ret);
+	
+	return ret;
+}
+
+static void tcp_port_cb(GtkSpinButton *spin, struct crazychat *cc)
+{
+	assert(spin);
+	assert(cc);
+	cc->tcp_port = gtk_spin_button_get_value_as_int(spin);
+	Debug("New tcp port: %d\n", cc->tcp_port);
+}
+
+static void udp_port_cb(GtkSpinButton *spin, struct crazychat *cc)
+{
+	assert(spin);
+	assert(cc);
+	cc->udp_port = gtk_spin_button_get_value_as_int(spin);
+	Debug("New udp port: %d\n", cc->udp_port);
+}
+
+static void features_enable_cb(struct crazychat *cc)
+{
+	Debug("Changing features state\n");
+	cc->features_state = !cc->features_state;
+	if (cc->features_state) {
+		cc->input_data = init_input(cc);
+	} else {
+		if (cc->input_data) {
+			gtk_widget_destroy(cc->input_data->widget);
+		}
+	}
+}
+
+static gboolean cc_signed_on(GaimConnection *gc, void *plugin)
+{
+	struct crazychat *extra;
+	void *conv_handle;
+
+	assert(plugin);
+	extra = (struct crazychat*)((GaimPlugin*)plugin)->info->extra_info;
+	gaim_signal_disconnect
+	    (gaim_connections_get_handle(), "signed-on",
+	     plugin, GAIM_CALLBACK(cc_signed_on));
+	gaim_signal_connect(GAIM_GTK_BLIST
+			    (gaim_get_blist()),
+			    "drawing-menu", plugin,
+			    GAIM_CALLBACK(cc_buddy_menu), NULL);
+	conv_handle = gaim_conversations_get_handle();
+	gaim_signal_connect(conv_handle, "received-im-msg", plugin,
+		GAIM_CALLBACK(receive_im_cb), extra);
+	gaim_signal_connect(conv_handle, "displaying-im-msg", plugin,
+		GAIM_CALLBACK(display_im_cb), extra);
+	return FALSE;
+}
+
+static gboolean plugin_load(GaimPlugin *plugin)
+{
+	GaimBuddyList *buddy_list;
+	void *conv_handle;
+
+	if (cc_init_gtk_gl())
+		return FALSE;
+
+	cc_init(&cc_info);
+	buddy_list = gaim_get_blist();
+	if (buddy_list) {
+		gaim_signal_connect(GAIM_GTK_BLIST
+				    (buddy_list),
+				    "drawing-menu", plugin,
+				    GAIM_CALLBACK(cc_buddy_menu), NULL);
+		conv_handle = gaim_conversations_get_handle();
+		gaim_signal_connect(conv_handle, "received-im-msg", plugin,
+			GAIM_CALLBACK(receive_im_cb), &cc_info);
+		gaim_signal_connect(conv_handle, "displaying-im-msg", plugin,
+			GAIM_CALLBACK(display_im_cb), &cc_info);
+	} else {
+		gaim_signal_connect
+		    (gaim_connections_get_handle(), "signed-on",
+		     plugin, GAIM_CALLBACK(cc_signed_on), plugin);
+	}
+
+	Debug("CrazyChat plugin loaded.\n");
+	
+	return TRUE;
+}
+
+static gboolean plugin_unload(GaimPlugin *plugin)
+{
+	void *conv_handle;
+	struct crazychat *extra;
+	assert(plugin);
+	extra = (struct crazychat*) plugin->info->extra_info;
+	cc_destroy(extra);
+	conv_handle = gaim_conversations_get_handle();
+	gaim_signal_disconnect(GAIM_GTK_BLIST
+			       (gaim_get_blist()),
+			       "drawing-menu", plugin,
+			       GAIM_CALLBACK(cc_buddy_menu));
+	gaim_signal_disconnect(conv_handle, "received-im", plugin,
+			       GAIM_CALLBACK(receive_im_cb));
+	gaim_signal_disconnect(conv_handle, "displaying-im-msg", plugin,
+			       GAIM_CALLBACK(display_im_cb));
+	Debug("CrazyChat plugin unloaded.\n");
+	return TRUE;
+}
+
+static void init_plugin(GaimPlugin *plugin)
+{
+	gtk_gl_init(NULL, NULL);
+	memset(&cc_info, 0, sizeof(cc_info));
+	Debug("CrazyChat plugin initialized\n");
+}
+
+GAIM_INIT_PLUGIN(crazychat, init_plugin, info)