#include "gtweakui.h"
#include "fileselect.h"
#include <gdk-pixbuf/gdk-pixbuf.h>

GladeXML *ws;
GConfClient *gc;
char *boolkeys[3] = {
	"/apps/gnome-session/options/auto_save_session",
	"/apps/gnome-session/options/logout_prompt",
	"/apps/gnome-session/options/show_splash_screen"
};
gboolean oldc[3], initc[3];
GtkWidget *c[3], *f;
GString *oldi, *initi;
gpointer p[3];

void doquit() {
	GSList *infos = NULL;
/* aargh.. this is not needed at all..
	int x;
	char *messages[3] = {"Save session automatically", "Show logout menu", "Show splash screen on login"};

	for (x = 0; x < 3; x ++)
		if (oldc[x] != initc[x])
			infos = g_slist_prepend(infos, messages[x]);
	
	if (!g_string_equal(oldi, initi))
		infos = g_slist_prepend(infos, "Splash image");

	if (infos != NULL) {
		gtk_widget_hide(xmlg(ws, "session"));
		notice(infos);
	}
*/
	g_string_free(oldi, TRUE);
	g_string_free(initi, TRUE);
	g_string_free(p[2], TRUE);
	if (infos != NULL) {
		g_slist_free(infos);
	} else {
		gtk_main_quit();
	}
}

void on_close_clicked(GtkWidget *w, gpointer data) {
	doquit();
}

gboolean delete_event(GtkWidget *w, GdkEvent *event, gpointer data) {
	doquit();
	return TRUE;
}

gboolean splash_update(const gchar *new) {
	static GtkWidget *label=NULL, *preview=NULL;
	GdkPixbuf *pimage, *ppreview;
	gchar *find;
	int x, y;

	if (label==NULL) {
		label = xmlg(ws, "splash_image_filename");
		preview = xmlg(ws, "splash_image_preview");
	}

	if (new[0] != '/') {
		new = gnome_program_locate_file(gtweakui, GNOME_FILE_DOMAIN_PIXMAP, new, FALSE, NULL);
		g_string_assign(oldi, new);
	}

	find = g_strrstr(new, "/");

	if (find != NULL) {
		pimage = gdk_pixbuf_new_from_file(new, NULL);
		if (pimage != NULL) {
			gtk_label_set_text(GTK_LABEL(label), find + 1);
			x = gdk_pixbuf_get_width(pimage);
			y = gdk_pixbuf_get_height(pimage);
			if ((x * 120 / y) > 160) {
				y = y * 160 / x;
				x = 160;
			} else {
				x = x * 120 / y;
				y = 120;
			}
			ppreview = gdk_pixbuf_scale_simple(pimage, x, y, GDK_INTERP_BILINEAR);
			g_object_unref(pimage);
			gtk_image_set_from_pixbuf(GTK_IMAGE(preview), ppreview);
			g_object_unref(ppreview);
			return TRUE;
		}
	}
	return FALSE;
}

void splash_gconf (GConfClient *client, guint cid, GConfEntry *e, gpointer d) {
	if ((gconf_entry_get_value(e) != NULL) && (gconf_entry_get_value(e)->type == GCONF_VALUE_STRING)) {
		const char *new;
		new = gconf_value_get_string(gconf_entry_get_value(e));
		if (g_utf8_collate(oldi->str, new) != 0)
			if (splash_update(new))
				g_string_assign(oldi, new);
	}
}

void splash_change (const gchar *filename) {
	if (filename != NULL)
		if (g_utf8_collate(oldi->str, filename) != 0) {
			if (splash_update(filename)) {
				g_string_assign(oldi, filename);
				gconf_client_set_string(gc, "/apps/gnome-session/options/splash_image", filename, NULL);
			} else {
				GtkWidget *dialog = gtk_message_dialog_new (NULL, GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_CLOSE, _("Error opening file, it may not be an image"));
				gtk_dialog_run (GTK_DIALOG (dialog));
				gtk_widget_destroy (dialog);
			}
		}
}

void gconfChangedCallback(GConfClient *client, guint cid, GConfEntry *e, gpointer d) {
	int i = (int)d;

	if ((gconf_entry_get_value(e) != NULL) && (gconf_entry_get_value(e)->type == GCONF_VALUE_BOOL)) {
		gboolean new = gconf_value_get_bool(gconf_entry_get_value(e));
		if (oldc[i] != new) {
			oldc[i] = new;
			gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(c[i]), new);
		}
	}
}

void checkboxcallback(GtkWidget *widget, gpointer data) {
	gboolean new = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget));
	int i = (int)data;
	if (new != oldc[i]) {
		oldc[i] = new;
		gconf_client_set_bool(gc, boolkeys[i], new, NULL);
	}
	if (i == 2)
		gtk_widget_set_sensitive (GTK_WIDGET(f), gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget)));
}

void hookupcallbacks() {
	int x;
	char key[3] = "c ";
	GtkWidget *dialog;
	
	gc = gconf_client_get_default();
	gconf_client_add_dir(gc, "/apps/gnome-session/options", GCONF_CLIENT_PRELOAD_NONE, NULL);

	xsc(ws, "close_button", "clicked", on_close_clicked, NULL);
	xsc(ws, "about_button", "clicked", about, xmlg(ws, "session"));
	xsc(ws, "session", "delete_event", delete_event, NULL);

	oldi = g_string_new(gconf_client_get_string(gc, "/apps/gnome-session/options/splash_image", NULL));

	if (!splash_update(oldi->str)) {
		GtkWidget *dialog = gtk_message_dialog_new (NULL, GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_CLOSE, _("Error opening current splash image.\n\nThe current splash image filename is:\n%s"), oldi->str);
		gtk_dialog_run (GTK_DIALOG (dialog));
		gtk_widget_destroy (dialog);
	}

	initi = g_string_new(oldi->str);

	p[0] = (gpointer *)splash_change;
	p[1] = (gpointer *)oldi;
	p[2] = g_string_new(_("Please select a splash image"));
	f = xmlg(ws, "splash_image");
//	gsc (f, "clicked", splash_clicked, NULL);
	gsc (f, "clicked", fileselect, p);
	gconfc(gc, "/apps/gnome-session/options/splash_image", splash_gconf, NULL);

	for (x = 0; x < 3; x ++) {
		key[1] = x + '0';
		c[x] = xmlg(ws, key);
		oldc[x] = initc[x] = gconf_client_get_bool (gc, boolkeys[x], NULL);
		gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(c[x]), initc[x]);
		gsc(c[x], "toggled", checkboxcallback, (gpointer)x);
		gconfc(gc, boolkeys[x], gconfChangedCallback, (gpointer)x);
	}
	
	gtk_widget_set_sensitive (GTK_WIDGET(f), gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(c[2])));

	gtk_widget_show_all(xmlg(ws, "session"));
}

int main(int argc, char *argv[]) {
	gtweakui = gnome_program_init(PACKAGE_NAME, PACKAGE_VERSION, LIBGNOMEUI_MODULE, argc, argv, GNOME_PARAM_APP_DATADIR, PACKAGE_DATA_DIR, NULL);
	gconf_init(argc, argv, NULL);
	
	bindtextdomain (GETTEXT_PACKAGE, GTWEAKUILOCALEDIR);
	bind_textdomain_codeset (GETTEXT_PACKAGE, "UTF-8");
	textdomain (GETTEXT_PACKAGE);

	ws = glade_xml_new(gnome_program_locate_file(gtweakui, GNOME_FILE_DOMAIN_APP_DATADIR, "session.glade", FALSE, NULL), NULL, NULL);

	hookupcallbacks();

	gtk_main();

	return 0;
}
