changeset 28977:2ecd4bc80500

merged with im.pidgin.pidgin
author Yoshiki Yazawa <yaz@honeyplanet.jp>
date Fri, 20 Nov 2009 16:36:33 +0900
parents 01a27787f8c9 (current diff) 38dd50309ba4 (diff)
children 1929b7a0c2c8
files libpurple/protocols/jabber/jabber.c pidgin/gtkconv.c pidgin/gtkprefs.c pidgin/gtkutils.c
diffstat 14 files changed, 594 insertions(+), 677 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog	Tue Nov 17 11:40:49 2009 +0900
+++ b/ChangeLog	Fri Nov 20 16:36:33 2009 +0900
@@ -44,6 +44,7 @@
 	* Fix a crash when adding a buddy without an '@'.
 	* Don't show the option to send a file to a buddy if we know for certain
 	  they don't support any file transfer method supported by libpurple.
+	* Keep the avatar on the server if one is not set locally.
 
 	Yahoo:
 	* Fix sending /buzz.
@@ -63,6 +64,31 @@
 	  widget name "pidgin_conv_userlist". (Heiko Schmitt)
 	* Add a hold button to the media window.
 
+	Pidgin Preference and Preference Window Changes:
+	* Removed the "Use font from theme" and "Conversation Font" preferences
+	  for everyone except Windows users.  The font can be controlled from the
+	  Pidgin GTK+ Theme Control plugin.
+	* Tabs in the Preferences window are now on the left side.
+	* The Browser tab is now visible for GNOME users.
+	* Added a Proxy tab shown no matter what environment Pidgin runs in.
+	* The Browser and Proxy tabs show appropriate GNOME-specific messages and
+	  allow launching the correct applications to change the relevant GNOME
+	  preferences if found.  These were previously together on the Network
+	  tab.
+	* Moved the port range spin buttons on the Network tab to be beside the
+	  checkbox that enables/disables them.
+	* Reorganized preferences on the Status/Idle tab to have one less
+	  "section."
+	* Reorganized preferences on the Sounds tab to have one less "section."
+	* Renamed Smiley Themes tab to Themes.
+	* Moved Buddy List Theme and Status Icon Theme selectors from Interface
+	  tab to Themes tab.
+	* Moved Sound Theme selector from Sounds tab to Themes tab.
+	* Changed the Smiley Theme selector to be consistent with the other theme
+	  selectors.
+	* Rearranged tabs such that Interface is first and all remaining tabs are
+	  alphabetized in English.
+
 version 2.6.3 (10/16/2009):
 	General:
 	* Fix a crash when performing DNS queries on Unixes that use the
--- a/libpurple/protocols/jabber/jabber.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/libpurple/protocols/jabber/jabber.c	Fri Nov 20 16:36:33 2009 +0900
@@ -3237,6 +3237,12 @@
 		GList *iter;
 		gboolean has_resources_without_caps = FALSE;
 
+		/* if we didn't find a JabberBuddy, we don't have presence for this
+		 buddy, let's assume they can receive files, disco should tell us
+		 when actually trying */
+		if (jb == NULL)
+			return TRUE;
+
 		/* find out if there is any resources without caps */
 		for (iter = jb->resources; iter ; iter = g_list_next(iter)) {
 			JabberBuddyResource *jbr = (JabberBuddyResource *) iter->data;
--- a/libpurple/protocols/jabber/usermood.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/libpurple/protocols/jabber/usermood.c	Fri Nov 20 16:36:33 2009 +0900
@@ -33,6 +33,7 @@
 static const char * const moodstrings[] = {
 	"afraid",
 	"amazed",
+	"amorous",
 	"angry",
 	"annoyed",
 	"anxious",
@@ -41,22 +42,31 @@
 	"bored",
 	"brave",
 	"calm",
+	"cautious",
 	"cold",
+	"confident",
 	"confused",
+	"contemplative",
 	"contented",
 	"cranky",
+	"crazy",
+	"creative",
 	"curious",
+	"dejected",
 	"depressed",
 	"disappointed",
 	"disgusted",
+	"dismayed",
 	"distracted",
 	"embarrassed",
+	"envious",
 	"excited",
 	"flirtatious",
 	"frustrated",
 	"grumpy",
 	"guilty",
 	"happy",
+	"hopeful",
 	"hot",
 	"humbled",
 	"humiliated",
@@ -71,13 +81,16 @@
 	"invincible",
 	"jealous",
 	"lonely",
+	"lucky",
 	"mean",
 	"moody",
 	"nervous",
 	"neutral",
 	"offended",
+	"outraged",
 	"playful",
 	"proud",
+	"relaxed",
 	"relieved",
 	"remorseful",
 	"restless",
@@ -88,20 +101,29 @@
 	"shy",
 	"sick",
 	"sleepy",
+	"spontaneous",
 	"stressed",
+	"strong",
 	"surprised",
+	"thankful",
 	"thirsty",
-	"worried",
-	NULL
+	"tired",
+	"weak",
+	"worried"
 };
 
-static void jabber_mood_cb(JabberStream *js, const char *from, xmlnode *items) {
-	/* it doesn't make sense to have more than one item here, so let's just pick the first one */
-	xmlnode *item = xmlnode_get_child(items, "item");
+static void
+jabber_mood_cb(JabberStream *js, const char *from, xmlnode *items)
+{
+	xmlnode *item;
+	JabberBuddy *buddy = jabber_buddy_find(js, from, FALSE);
 	const char *newmood = NULL;
 	char *moodtext = NULL;
-	JabberBuddy *buddy = jabber_buddy_find(js, from, FALSE);
-	xmlnode *moodinfo, *mood;
+	xmlnode *child, *mood;
+
+	/* it doesn't make sense to have more than one item here, so let's just pick the first one */
+	item = xmlnode_get_child(items, "item");
+
 	/* ignore the mood of people not on our buddy list */
 	if (!buddy || !item)
 		return;
@@ -109,35 +131,39 @@
 	mood = xmlnode_get_child_with_namespace(item, "mood", "http://jabber.org/protocol/mood");
 	if (!mood)
 		return;
-	for (moodinfo = mood->child; moodinfo; moodinfo = moodinfo->next) {
-		if (moodinfo->type == XMLNODE_TYPE_TAG) {
-			if (!strcmp(moodinfo->name, "text")) {
-				if (!moodtext) /* only pick the first one */
-					moodtext = xmlnode_get_data(moodinfo);
-			} else {
-				int i;
-				for (i = 0; moodstrings[i]; ++i) {
-					/* verify that the mood is known (valid) */
-					if (!strcmp(moodinfo->name, moodstrings[i])) {
-						newmood = moodstrings[i];
-						break;
-					}
+	for (child = mood->child; child; child = child->next) {
+		if (child->type != XMLNODE_TYPE_TAG)
+			continue;
+
+		if (g_str_equal("text", child->name) && moodtext == NULL)
+				moodtext = xmlnode_get_data(child);
+		else {
+			int i;
+			for (i = 0; i < G_N_ELEMENTS(moodstrings); ++i) {
+				/* verify that the mood is known (valid) */
+				if (g_str_equal(child->name, moodstrings[i])) {
+					newmood = moodstrings[i];
+					break;
 				}
 			}
-			if (newmood != NULL && moodtext != NULL)
-			   break;
 		}
+		if (newmood != NULL && moodtext != NULL)
+		   break;
 	}
 	if (newmood != NULL) {
+		PurpleAccount *account;
 		const char *status_id;
 		JabberBuddyResource *resource = jabber_buddy_find_resource(buddy, NULL);
-		if(!resource) { /* huh? */
+		if (!resource) { /* huh? */
 			g_free(moodtext);
 			return;
 		}
 		status_id = jabber_buddy_state_get_status_id(resource->state);
 
-		purple_prpl_got_user_status(js->gc->account, from, status_id, "mood", _(newmood), "moodtext", moodtext?moodtext:"", NULL);
+		account = purple_connection_get_account(js->gc);
+		purple_prpl_got_user_status(account, from, status_id, "mood",
+		                            _(newmood), "moodtext",
+		                            moodtext ? moodtext : "", NULL);
 	}
 	g_free(moodtext);
 }
@@ -149,7 +175,6 @@
 
 static void do_mood_set_from_fields(PurpleConnection *gc, PurpleRequestFields *fields) {
 	JabberStream *js;
-	const int max_mood_idx = sizeof(moodstrings) / sizeof(moodstrings[0]) - 1;
 	int selected_mood = purple_request_fields_get_choice(fields, "mood");
 
 	if (!PURPLE_CONNECTION_IS_VALID(gc)) {
@@ -159,7 +184,7 @@
 
 	js = gc->proto_data;
 
-	if (selected_mood < 0 || selected_mood >= max_mood_idx) {
+	if (selected_mood < 0 || selected_mood >= G_N_ELEMENTS(moodstrings)) {
 		purple_debug_error("jabber", "Invalid mood index (%d) selected.\n", selected_mood);
 		return;
 	}
@@ -182,7 +207,7 @@
 	field = purple_request_field_choice_new("mood",
 											_("Mood"), 0);
 
-	for(i = 0; moodstrings[i]; ++i)
+	for(i = 0; i < G_N_ELEMENTS(moodstrings); ++i)
 		purple_request_field_choice_add(field, _(moodstrings[i]));
 
 	purple_request_field_set_required(field, TRUE);
--- a/libpurple/protocols/mxit/actions.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/libpurple/protocols/mxit/actions.c	Fri Nov 20 16:36:33 2009 +0900
@@ -41,17 +41,17 @@
 
 /* MXit Moods */
 static const char*	moods[] = {
-	/* 0 */		"None",
-	/* 1 */		"Angry",
-	/* 2 */		"Excited",
-	/* 3 */		"Grumpy",
-	/* 4 */		"Happy",
-	/* 5 */		"In Love",
-	/* 6 */		"Invincible",
-	/* 7 */		"Sad",
-	/* 8 */		"Hot",
-	/* 9 */		"Sick",
-	/* 10 */	"Sleepy"
+	/* 0 */		N_("None"),
+	/* 1 */		N_("Angry"),
+	/* 2 */		N_("Excited"),
+	/* 3 */		N_("Grumpy"),
+	/* 4 */		N_("Happy"),
+	/* 5 */		N_("In Love"),
+	/* 6 */		N_("Invincible"),
+	/* 7 */		N_("Sad"),
+	/* 8 */		N_("Hot"),
+	/* 9 */		N_("Sick"),
+	/* 10 */	N_("Sleepy")
 };
 
 
--- a/libpurple/protocols/mxit/mxit.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/libpurple/protocols/mxit/mxit.c	Fri Nov 20 16:36:33 2009 +0900
@@ -541,7 +541,7 @@
 
 	table = g_hash_table_new( g_str_hash, g_str_equal );
 
-	g_hash_table_insert( table, "login_label", _( "Your Mobile Number..." ) );
+	g_hash_table_insert( table, "login_label", (gpointer)_( "Your Mobile Number..." ) );
 
 	return table;
 }
--- a/libpurple/protocols/mxit/mxit.h	Tue Nov 17 11:40:49 2009 +0900
+++ b/libpurple/protocols/mxit/mxit.h	Fri Nov 20 16:36:33 2009 +0900
@@ -27,14 +27,7 @@
 #define		_MXIT_H_
 
 
-/* internationalize feedback strings */
-#ifndef		_
-#ifdef		GETTEXT_PACKAGE
-#include	<glib/gi18n-lib.h>
-#else
-#define		_( x )						( x )
-#endif
-#endif
+#include "internal.h"
 
 
 #if defined( __APPLE__ )
--- a/libpurple/protocols/mxit/splashscreen.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/libpurple/protocols/mxit/splashscreen.c	Fri Nov 20 16:36:33 2009 +0900
@@ -23,7 +23,6 @@
  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02111-1301  USA
  */
 
-#include <libgen.h>
 #include <glib/gstdio.h>
 
 #include "purple.h"
--- a/libpurple/tests/test_jabber_jutil.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/libpurple/tests/test_jabber_jutil.c	Fri Nov 20 16:36:33 2009 +0900
@@ -40,6 +40,8 @@
 	fail_unless(jabber_nodeprep_validate("foo"));
 	fail_unless(jabber_nodeprep_validate("%d"));
 	fail_unless(jabber_nodeprep_validate("y\\z"));
+	fail_unless(jabber_nodeprep_validate("a="));
+	fail_unless(jabber_nodeprep_validate("a,"));
 
 	longnode = g_strnfill(1023, 'a');
 	fail_unless(jabber_nodeprep_validate(longnode));
@@ -118,6 +120,8 @@
 	assert_valid_jid("paul@[::1]"); /* IPv6 */
 	assert_valid_jid("paul@[2001:470:1f05:d58::2]");
 	assert_valid_jid("paul@[2001:470:1f05:d58::2]/foo");
+	assert_valid_jid("pa=ul@10.0.42.230");
+	assert_valid_jid("pa,ul@10.0.42.230");
 
 	assert_invalid_jid("@gmail.com");
 	assert_invalid_jid("@@gmail.com");
--- a/pidgin/gtkconv.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/pidgin/gtkconv.c	Fri Nov 20 16:36:33 2009 +0900
@@ -8061,8 +8061,10 @@
 	purple_prefs_add_int(PIDGIN_PREFS_ROOT "/conversations/tab_side", GTK_POS_TOP);
 	purple_prefs_add_int(PIDGIN_PREFS_ROOT "/conversations/scrollback_lines", 4000);
 
+#ifdef _WIN32
 	purple_prefs_add_bool(PIDGIN_PREFS_ROOT "/conversations/use_theme_font", TRUE);
 	purple_prefs_add_string(PIDGIN_PREFS_ROOT "/conversations/custom_font", "");
+#endif
 
 	/* Conversations -> Chat */
 	purple_prefs_add_none(PIDGIN_PREFS_ROOT "/conversations/chat");
--- a/pidgin/gtkprefs.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/pidgin/gtkprefs.c	Fri Nov 20 16:36:33 2009 +0900
@@ -74,23 +74,20 @@
 static GtkWidget *prefsnotebook;
 
 static GtkWidget *sound_entry = NULL;
-static GtkListStore *smiley_theme_store = NULL;
-static GtkTreeSelection *smiley_theme_sel = NULL;
-static GtkWidget *prefs_proxy_frame = NULL;
-static GtkWidget *prefs_proxy_subframe = NULL;
 
 static GtkWidget *prefs = NULL;
 static GtkWidget *debugbutton = NULL;
 static int notebook_page = 0;
-static GtkTreeRowReference *previous_smiley_row = NULL;
 
 static GtkListStore *prefs_sound_themes;
 static GtkListStore *prefs_blist_themes;
 static GtkListStore *prefs_status_icon_themes;
+static GtkListStore *prefs_smiley_themes;
 
 static GtkWidget *prefs_sound_themes_combo_box;
 static GtkWidget *prefs_blist_themes_combo_box;
 static GtkWidget *prefs_status_themes_combo_box;
+static GtkWidget *prefs_smiley_themes_combo_box;
 
 static gboolean prefs_sound_themes_loading;
 
@@ -341,123 +338,6 @@
 	sound_entry = NULL;
 	debugbutton = NULL;
 	notebook_page = 0;
-	smiley_theme_store = NULL;
-	if (previous_smiley_row)
-		gtk_tree_row_reference_free(previous_smiley_row);
-	previous_smiley_row = NULL;
-
-}
-
-static void
-smiley_sel(GtkTreeSelection *sel, GtkTreeModel *model)
-{
-	GtkTreeIter  iter;
-	const char *themename;
-	char *description;
-	GValue val;
-	GtkTreePath *path, *oldpath;
-	struct smiley_theme *new_theme, *old_theme;
-	GtkWidget *remove_button = g_object_get_data(G_OBJECT(sel), "remove_button");
-
-	if (!gtk_tree_selection_get_selected(sel, &model, &iter)) {
-		gtk_widget_set_sensitive(remove_button, FALSE);
-		return;
-	}
-
-	old_theme = current_smiley_theme;
-	val.g_type = 0;
-	gtk_tree_model_get_value(model, &iter, 3, &val);
-	path = gtk_tree_model_get_path(model, &iter);
-	themename = g_value_get_string(&val);
-	purple_prefs_set_string(PIDGIN_PREFS_ROOT "/smileys/theme", themename);
-
-	gtk_widget_set_sensitive(remove_button, (strcmp(themename, "none") &&
-	                                         strcmp(themename, _("Default"))));
-	g_value_unset (&val);
-
-	/* current_smiley_theme is set in callback for the above pref change */
-	new_theme = current_smiley_theme;
-	description = g_strdup_printf("<span size='larger' weight='bold'>%s</span> - %s\n"
-								"<span size='smaller' foreground='white'>%s</span>",
-								_(new_theme->name), _(new_theme->author), _(new_theme->desc));
-	gtk_list_store_set(smiley_theme_store, &iter, 1, description, -1);
-	g_free(description);
-
-	if (new_theme != old_theme && previous_smiley_row) {
-		oldpath = gtk_tree_row_reference_get_path(previous_smiley_row);
-		if (gtk_tree_model_get_iter(model, &iter, oldpath)) {
-			description = g_strdup_printf("<span size='larger' weight='bold'>%s</span> - %s\n"
-								"<span size='smaller' foreground='dim grey'>%s</span>",
-								_(old_theme->name), _(old_theme->author), _(old_theme->desc));
-			gtk_list_store_set(smiley_theme_store, &iter, 1,
-				description, -1);
-			g_free(description);
-		}
-		gtk_tree_path_free(oldpath);
-	}
-	if (previous_smiley_row)
-		gtk_tree_row_reference_free(previous_smiley_row);
-	previous_smiley_row = gtk_tree_row_reference_new(model, path);
-	gtk_tree_path_free(path);
-}
-
-static GtkTreeRowReference *
-theme_refresh_theme_list(void)
-{
-	GdkPixbuf *pixbuf;
-	GSList *themes;
-	GtkTreeIter iter;
-	GtkTreeRowReference *row_ref = NULL;
-
-	if (previous_smiley_row)
-		gtk_tree_row_reference_free(previous_smiley_row);
-	previous_smiley_row = NULL;
-
-	pidgin_themes_smiley_theme_probe();
-
-	if (!(themes = smiley_themes))
-		return NULL;
-
-	gtk_list_store_clear(smiley_theme_store);
-
-	while (themes) {
-		struct smiley_theme *theme = themes->data;
-		char *description = g_strdup_printf("<span size='larger' weight='bold'>%s</span> - %s\n"
-						    "<span size='smaller' foreground='dim grey'>%s</span>",
-						    _(theme->name), _(theme->author), _(theme->desc));
-		gtk_list_store_append (smiley_theme_store, &iter);
-
-		/*
-		 * LEAK - Gentoo memprof thinks pixbuf is leaking here... but it
-		 * looks like it should be ok to me.  Anyone know what's up?  --Mark
-		 */
-		pixbuf = (theme->icon ? gdk_pixbuf_new_from_file(theme->icon, NULL) : NULL);
-
-		gtk_list_store_set(smiley_theme_store, &iter,
-				   0, pixbuf,
-				   1, description,
-				   2, theme->path,
-				   3, theme->name,
-				   -1);
-
-		if (pixbuf != NULL)
-			g_object_unref(G_OBJECT(pixbuf));
-
-		g_free(description);
-		themes = themes->next;
-
-		/* If this is the currently selected theme,
-		 * we will need to select it. Grab the row reference. */
-		if (theme == current_smiley_theme) {
-			GtkTreePath *path = gtk_tree_model_get_path(
-				GTK_TREE_MODEL(smiley_theme_store), &iter);
-			row_ref = gtk_tree_row_reference_new(
-				GTK_TREE_MODEL(smiley_theme_store), path);
-			gtk_tree_path_free(path);
-		}
-	}
-
-	return row_ref;
 }
 
 static gchar *
@@ -471,6 +351,44 @@
 						   description != NULL ? description : "");
 }
 
+static void
+smileys_refresh_theme_list(void)
+{
+	GdkPixbuf *pixbuf;
+	GSList *themes;
+	GtkTreeIter iter;
+
+	pidgin_themes_smiley_theme_probe();
+
+	if (!(themes = smiley_themes))
+		return;
+
+	while (themes) {
+		struct smiley_theme *theme = themes->data;
+		char *description = get_theme_markup(_(theme->name), FALSE,
+		                                     _(theme->author), _(theme->desc));
+		gtk_list_store_append(prefs_smiley_themes, &iter);
+
+		/*
+		 * LEAK - Gentoo memprof thinks pixbuf is leaking here... but it
+		 * looks like it should be ok to me.  Anyone know what's up?  --Mark
+		 */
+		pixbuf = (theme->icon ? gdk_pixbuf_new_from_file(theme->icon, NULL) : NULL);
+
+		gtk_list_store_set(prefs_smiley_themes, &iter,
+				   0, pixbuf,
+				   1, description,
+				   2, theme->name,
+				   -1);
+
+		if (pixbuf != NULL)
+			g_object_unref(G_OBJECT(pixbuf));
+
+		g_free(description);
+		themes = themes->next;
+	}
+}
+
 /* Rebuild the markup for the sound theme selection for "(Custom)" themes */
 static void
 pref_sound_generate_markup(void)
@@ -492,8 +410,8 @@
 
 			if (!name || *name == '\0') {
 				g_free(name);
-				name = g_strdup(_("(Default)"));
-				author = _("None");
+				name = g_strdup(_("Default"));
+				author = _("Penguin Pimps");
 				description = _("The default Pidgin sound theme");
 			} else {
 				theme = PURPLE_SOUND_THEME(purple_theme_manager_find_theme(name, "sound"));
@@ -613,7 +531,7 @@
 	/* blist themes */
 	gtk_list_store_clear(prefs_blist_themes);
 	gtk_list_store_append(prefs_blist_themes, &iter);
-	tmp = get_theme_markup(_("(Default)"), FALSE, _("None"),
+	tmp = get_theme_markup(_("Default"), FALSE, _("Penguin Pimps"),
 		_("The default Pidgin buddy list theme"));
 	gtk_list_store_set(prefs_blist_themes, &iter, 0, pixbuf, 1, tmp, 2, "", -1);
 	g_free(tmp);
@@ -621,20 +539,25 @@
 	/* status icon themes */
 	gtk_list_store_clear(prefs_status_icon_themes);
 	gtk_list_store_append(prefs_status_icon_themes, &iter);
-	tmp = get_theme_markup(_("(Default)"), FALSE, _("None"),
+	tmp = get_theme_markup(_("Default"), FALSE, _("Penguin Pimps"),
 		_("The default Pidgin status icon theme"));
 	gtk_list_store_set(prefs_status_icon_themes, &iter, 0, pixbuf, 1, tmp, 2, "", -1);
 	g_free(tmp);
 	if (pixbuf)
 		g_object_unref(G_OBJECT(pixbuf));
 
+	/* smiley themes */
+	gtk_list_store_clear(prefs_smiley_themes);
+
 	purple_theme_manager_for_each_theme(prefs_themes_sort);
 	pref_sound_generate_markup();
+	smileys_refresh_theme_list();
 
 	/* set active */
 	prefs_set_active_theme_combo(prefs_sound_themes_combo_box, prefs_sound_themes, purple_prefs_get_string(PIDGIN_PREFS_ROOT "/sound/theme"));
 	prefs_set_active_theme_combo(prefs_blist_themes_combo_box, prefs_blist_themes, purple_prefs_get_string(PIDGIN_PREFS_ROOT "/blist/theme"));
 	prefs_set_active_theme_combo(prefs_status_themes_combo_box, prefs_status_icon_themes, purple_prefs_get_string(PIDGIN_PREFS_ROOT "/status/icon-theme"));
+	prefs_set_active_theme_combo(prefs_smiley_themes_combo_box, prefs_smiley_themes, purple_prefs_get_string(PIDGIN_PREFS_ROOT "/smileys/theme"));
 	prefs_sound_themes_loading = FALSE;
 }
 
@@ -647,6 +570,8 @@
 	prefs_blist_themes = gtk_list_store_new(3, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING);
 
 	prefs_status_icon_themes = gtk_list_store_new(3, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING);
+
+	prefs_smiley_themes = gtk_list_store_new(3, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING);
 }
 
 static PurpleTheme *
@@ -714,7 +639,6 @@
 #endif
 	gchar *destdir;
 	const char *tail;
-	GtkTreeRowReference *theme_rowref;
 	gboolean is_smiley_theme, is_archive;
 	PurpleTheme *theme = NULL;
 
@@ -773,16 +697,7 @@
 
 	if (is_smiley_theme) {
 		/* just extract the folder to the smiley directory */
-		theme_rowref = theme_refresh_theme_list();
-
-		if (theme_rowref != NULL) {
-			GtkTreePath *tp = gtk_tree_row_reference_get_path(theme_rowref);
-
-			if (tp)
-				gtk_tree_selection_select_path(smiley_theme_sel, tp);
-
-			gtk_tree_row_reference_free(theme_rowref);
-		}
+		prefs_themes_refresh();
 
 	} else if (is_archive) {
 		theme = prefs_theme_find_theme(destdir, info->type);
@@ -1022,6 +937,23 @@
 	}
 }
 
+/* sets the current smiley theme */
+static void
+prefs_set_smiley_theme_cb(GtkComboBox *combo_box, gpointer user_data)
+{
+	gchar *new_theme;
+	GtkTreeIter new_iter;
+
+	if (gtk_combo_box_get_active_iter(combo_box, &new_iter)) {
+
+		gtk_tree_model_get(GTK_TREE_MODEL(prefs_smiley_themes), &new_iter, 2, &new_theme, -1);
+
+		purple_prefs_set_string(PIDGIN_PREFS_ROOT "/smileys/theme", new_theme);
+
+		g_free(new_theme);
+	}
+}
+
 
 /* Does same as normal sort, except "none" is sorted first */
 static gint pidgin_sort_smileys (GtkTreeModel	*model,
@@ -1032,8 +964,8 @@
 	gint ret = 0;
 	gchar *name1 = NULL, *name2 = NULL;
 
-	gtk_tree_model_get(model, a, 3, &name1, -1);
-	gtk_tree_model_get(model, b, 3, &name2, -1);
+	gtk_tree_model_get(model, a, 2, &name1, -1);
+	gtk_tree_model_get(model, b, 2, &name2, -1);
 
 	if (name1 == NULL || name2 == NULL) {
 		if (!(name1 == NULL && name2 == NULL))
@@ -1049,7 +981,7 @@
 		ret = 1;
 	} else {
 		/* Neither string is "none", default to normal sort */
-		ret = purple_utf8_strcasecmp(name1,name2);
+		ret = purple_utf8_strcasecmp(name1, name2);
 	}
 
 	g_free(name1);
@@ -1058,158 +990,154 @@
 	return ret;
 }
 
+/* sets the current buddy list theme */
 static void
-request_theme_file_name_cb(gpointer data, char *theme_file_name)
-{
-	struct theme_info *info = g_new0(struct theme_info, 1);
-	info->type = g_strdup("smiley");
-
-	theme_install_theme(theme_file_name, info);
-}
-
-static void
-add_theme_button_clicked_cb(GtkWidget *widget, gpointer user_data)
-{
-	purple_request_file(NULL, _("Install Theme"), NULL, FALSE, (GCallback)request_theme_file_name_cb, NULL, NULL, NULL, NULL, NULL);
-}
-
-static void
-remove_theme_button_clicked_cb(GtkWidget *button, GtkTreeView *tv)
+prefs_set_blist_theme_cb(GtkComboBox *combo_box, gpointer user_data)
 {
-	char *theme_name = NULL, *theme_file = NULL;
-	GtkTreeModel *tm;
-	GtkTreeIter itr;
-	GtkTreeRowReference *trr = NULL;
-
-	if ((tm = gtk_tree_view_get_model(tv)) == NULL)
-		return;
-	if (!gtk_tree_selection_get_selected(smiley_theme_sel, NULL, &itr))
-		return;
-	gtk_tree_model_get(tm, &itr, 2, &theme_file, 3, &theme_name, -1);
-
-	if (theme_file && theme_name && strcmp(theme_name, "none"))
-		pidgin_themes_remove_smiley_theme(theme_file);
-
-	if ((trr = theme_refresh_theme_list()) != NULL) {
-		GtkTreePath *tp = gtk_tree_row_reference_get_path(trr);
-
-		if (tp) {
-			gtk_tree_selection_select_path(smiley_theme_sel, tp);
-			gtk_tree_path_free(tp);
-		}
-		gtk_tree_row_reference_free(trr);
+	PidginBlistTheme *theme =  NULL;
+	GtkTreeIter iter;
+	gchar *name = NULL;
+
+	if(gtk_combo_box_get_active_iter(combo_box, &iter)) {
+
+		gtk_tree_model_get(GTK_TREE_MODEL(prefs_blist_themes), &iter, 2, &name, -1);
+
+		if(!name || !g_str_equal(name, ""))
+			theme = PIDGIN_BLIST_THEME(purple_theme_manager_find_theme(name, "blist"));
+
+		g_free(name);
+
+		pidgin_blist_set_theme(theme);
 	}
-
-	g_free(theme_file);
-	g_free(theme_name);
+}
+
+/* sets the current icon theme */
+static void
+prefs_set_status_icon_theme_cb(GtkComboBox *combo_box, gpointer user_data)
+{
+	PidginStatusIconTheme *theme = NULL;
+	GtkTreeIter iter;
+	gchar *name = NULL;
+
+	if(gtk_combo_box_get_active_iter(combo_box, &iter)) {
+
+		gtk_tree_model_get(GTK_TREE_MODEL(prefs_status_icon_themes), &iter, 2, &name, -1);
+
+		if(!name || !g_str_equal(name, ""))
+			theme = PIDGIN_STATUS_ICON_THEME(purple_theme_manager_find_theme(name, "status-icon"));
+
+		g_free(name);
+
+		pidgin_stock_load_status_icon_theme(theme);
+		pidgin_blist_refresh(purple_get_blist());
+	}
 }
 
 static GtkWidget *
 theme_page(void)
 {
-	GtkWidget *add_button, *remove_button;
-	GtkWidget *hbox_buttons;
-	GtkWidget *alignment;
-	GtkWidget *ret;
-	GtkWidget *sw;
-	GtkWidget *view;
-	GtkCellRenderer *rend;
-	GtkTreeViewColumn *col;
-	GtkTreeSelection *sel;
-	GtkTreeRowReference *rowref;
+	GtkWidget *ret, *vbox;
 	GtkWidget *label;
-	GtkTargetEntry te[3] = {
-		{"text/plain", 0, 0},
-		{"text/uri-list", 0, 1},
-		{"STRING", 0, 2}
-	};
+	GtkWidget *themesel_hbox;
+	GtkSizeGroup *label_sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
+	GtkSizeGroup *combo_sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
 
 	ret = gtk_vbox_new(FALSE, PIDGIN_HIG_CAT_SPACE);
 	gtk_container_set_border_width (GTK_CONTAINER (ret), PIDGIN_HIG_BORDER);
 
-	label = gtk_label_new(_("Select a smiley theme that you would like to use from the list below."
-	                        " New themes can be installed by dragging and dropping them onto the theme list."));
-
-	gtk_label_set_line_wrap(GTK_LABEL(label), TRUE);
+	vbox = pidgin_make_frame(ret, _("Theme Selections"));
+
+	/* Instructions */
+	label = gtk_label_new(_("Select a theme that you would like to use from "
+							"the lists below.\nNew themes can be installed by "
+							"dragging and dropping them onto the theme list."));
+
 	gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
 	gtk_label_set_justify(GTK_LABEL(label), GTK_JUSTIFY_LEFT);
 
-	gtk_box_pack_start(GTK_BOX(ret), label, TRUE, TRUE, 0);
+	gtk_box_pack_start(GTK_BOX(vbox), label, TRUE, FALSE, 0);
 	gtk_widget_show(label);
 
-	sw = gtk_scrolled_window_new(NULL,NULL);
-	gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC, GTK_POLICY_ALWAYS);
-	gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw), GTK_SHADOW_IN);
-
-	gtk_box_pack_start(GTK_BOX(ret), sw, TRUE, TRUE, 0);
-	smiley_theme_store = gtk_list_store_new (4, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING);
-
-	rowref = theme_refresh_theme_list();
-
-	view = gtk_tree_view_new_with_model (GTK_TREE_MODEL(smiley_theme_store));
-
-	gtk_drag_dest_set(view, GTK_DEST_DEFAULT_MOTION | GTK_DEST_DEFAULT_HIGHLIGHT | GTK_DEST_DEFAULT_DROP, te,
-					sizeof(te) / sizeof(GtkTargetEntry) , GDK_ACTION_COPY | GDK_ACTION_MOVE);
-
-	g_signal_connect(G_OBJECT(view), "drag_data_received", G_CALLBACK(theme_dnd_recv), "smiley");
-
-	rend = gtk_cell_renderer_pixbuf_new();
-	smiley_theme_sel = sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (view));
+	/* Buddy List Themes */
+	themesel_hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+
+	label = gtk_label_new(_("Buddy List Theme:"));
+	gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
+	gtk_size_group_add_widget(label_sg, label);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), label, FALSE, FALSE, 0);
+
+	prefs_blist_themes_combo_box = prefs_build_theme_combo_box(prefs_blist_themes,
+						purple_prefs_get_string(PIDGIN_PREFS_ROOT "/blist/theme"),
+						"blist");
+	g_signal_connect(G_OBJECT(prefs_blist_themes_combo_box), "changed",
+						(GCallback)prefs_set_blist_theme_cb, NULL);
+	gtk_size_group_add_widget(combo_sg, prefs_blist_themes_combo_box);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), prefs_blist_themes_combo_box, FALSE, FALSE, 0);
+
+	gtk_box_pack_start(GTK_BOX(vbox), themesel_hbox, FALSE, FALSE, 0);
+
+	/* Status Icon Themes */
+	themesel_hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+
+	label = gtk_label_new(_("Status Icon Theme:"));
+	gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
+	gtk_size_group_add_widget(label_sg, label);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), label, FALSE, FALSE, 0);
+
+	prefs_status_themes_combo_box = prefs_build_theme_combo_box(prefs_status_icon_themes,
+						purple_prefs_get_string(PIDGIN_PREFS_ROOT "/status/icon-theme"),
+						"icon");
+	g_signal_connect(G_OBJECT(prefs_status_themes_combo_box), "changed",
+						(GCallback)prefs_set_status_icon_theme_cb, NULL);
+	gtk_size_group_add_widget(combo_sg, prefs_status_themes_combo_box);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), prefs_status_themes_combo_box, FALSE, FALSE, 0);
+
+	gtk_box_pack_start(GTK_BOX(vbox), themesel_hbox, FALSE, FALSE, 0);
+
+	/* Sound Themes */
+	themesel_hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+
+	label = gtk_label_new(_("Sound Theme:"));
+	gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
+	gtk_size_group_add_widget(label_sg, label);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), label, FALSE, FALSE, 0);
+
+	prefs_sound_themes_combo_box = prefs_build_theme_combo_box(prefs_sound_themes,
+						purple_prefs_get_string(PIDGIN_PREFS_ROOT "/sound/theme"),
+						"sound");
+	g_signal_connect(G_OBJECT(prefs_sound_themes_combo_box), "changed",
+						(GCallback)prefs_set_sound_theme_cb, NULL);
+	gtk_size_group_add_widget(combo_sg, prefs_sound_themes_combo_box);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), prefs_sound_themes_combo_box, FALSE, FALSE, 0);
+
+	gtk_box_pack_start(GTK_BOX(vbox), themesel_hbox, FALSE, FALSE, 0);
+
+	/* Smiley Themes */
+	themesel_hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+
+	label = gtk_label_new(_("Smiley Theme:"));
+	gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
+	gtk_size_group_add_widget(label_sg, label);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), label, FALSE, FALSE, 0);
+
+	prefs_smiley_themes_combo_box = prefs_build_theme_combo_box(prefs_smiley_themes,
+						purple_prefs_get_string(PIDGIN_PREFS_ROOT "/smileys/theme"),
+						"smiley");
+	g_signal_connect(G_OBJECT(prefs_smiley_themes_combo_box), "changed",
+						(GCallback)prefs_set_smiley_theme_cb, NULL);
+	gtk_size_group_add_widget(combo_sg, prefs_smiley_themes_combo_box);
+	gtk_box_pack_start(GTK_BOX(themesel_hbox), prefs_smiley_themes_combo_box, FALSE, FALSE, 0);
+
+	gtk_box_pack_start(GTK_BOX(vbox), themesel_hbox, FALSE, FALSE, 0);
 
 	/* Custom sort so "none" theme is at top of list */
-	gtk_tree_sortable_set_sort_func(GTK_TREE_SORTABLE(smiley_theme_store),
-									3, pidgin_sort_smileys, NULL, NULL);
-
-	gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(smiley_theme_store),
-										 3, GTK_SORT_ASCENDING);
-
-	col = gtk_tree_view_column_new_with_attributes (_("Icon"),
-							rend,
-							"pixbuf", 0,
-							NULL);
-	gtk_tree_view_append_column (GTK_TREE_VIEW(view), col);
-
-	rend = gtk_cell_renderer_text_new();
-	col = gtk_tree_view_column_new_with_attributes (_("Description"),
-							rend,
-							"markup", 1,
-							NULL);
-	gtk_tree_view_append_column (GTK_TREE_VIEW(view), col);
-	g_object_unref(G_OBJECT(smiley_theme_store));
-	gtk_container_add(GTK_CONTAINER(sw), view);
-
-	g_signal_connect(G_OBJECT(sel), "changed", G_CALLBACK(smiley_sel), NULL);
-
-	alignment = gtk_alignment_new(1.0, 0.5, 0.0, 1.0);
-	gtk_widget_show(alignment);
-	gtk_box_pack_start(GTK_BOX(ret), alignment, FALSE, TRUE, 0);
-
-	hbox_buttons = gtk_hbox_new(TRUE, PIDGIN_HIG_CAT_SPACE);
-	gtk_widget_show(hbox_buttons);
-	gtk_container_add(GTK_CONTAINER(alignment), hbox_buttons);
-
-	add_button = gtk_button_new_from_stock(GTK_STOCK_ADD);
-	gtk_widget_show(add_button);
-	gtk_box_pack_start(GTK_BOX(hbox_buttons), add_button, FALSE, TRUE, 0);
-	g_signal_connect(G_OBJECT(add_button), "clicked", (GCallback)add_theme_button_clicked_cb, view);
-
-	remove_button = gtk_button_new_from_stock(GTK_STOCK_REMOVE);
-	gtk_widget_show(remove_button);
-	gtk_box_pack_start(GTK_BOX(hbox_buttons), remove_button, FALSE, TRUE, 0);
-	g_signal_connect(G_OBJECT(remove_button), "clicked", (GCallback)remove_theme_button_clicked_cb, view);
-	g_object_set_data(G_OBJECT(sel), "remove_button", remove_button);
-
-	if (rowref) {
-		GtkTreePath *path = gtk_tree_row_reference_get_path(rowref);
-		gtk_tree_row_reference_free(rowref);
-		gtk_tree_selection_select_path(sel, path);
-		gtk_tree_path_free(path);
-	}
+	gtk_tree_sortable_set_sort_func(GTK_TREE_SORTABLE(prefs_smiley_themes),
+	                                2, pidgin_sort_smileys, NULL, NULL);
+	gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(prefs_smiley_themes),
+										 2, GTK_SORT_ASCENDING);
 
 	gtk_widget_show_all(ret);
 
-	pidgin_set_accessible_label (view, label);
-
 	return ret;
 }
 
@@ -1407,49 +1335,6 @@
 	gtk_box_pack_start(GTK_BOX(vbox), checkbox, FALSE, FALSE, 0);
 }
 
-/* sets the current buddy list theme */
-static void
-prefs_set_blist_theme_cb(GtkComboBox *combo_box, gpointer user_data)
-{
-	PidginBlistTheme *theme =  NULL;
-	GtkTreeIter iter;
-	gchar *name = NULL;
-
-	if(gtk_combo_box_get_active_iter(combo_box, &iter)) {
-
-		gtk_tree_model_get(GTK_TREE_MODEL(prefs_blist_themes), &iter, 2, &name, -1);
-
-		if(!name || !g_str_equal(name, ""))
-			theme = PIDGIN_BLIST_THEME(purple_theme_manager_find_theme(name, "blist"));
-
-		g_free(name);
-
-		pidgin_blist_set_theme(theme);
-	}
-}
-
-/* sets the current icon theme */
-static void
-prefs_set_status_icon_theme_cb(GtkComboBox *combo_box, gpointer user_data)
-{
-	PidginStatusIconTheme *theme = NULL;
-	GtkTreeIter iter;
-	gchar *name = NULL;
-
-	if(gtk_combo_box_get_active_iter(combo_box, &iter)) {
-
-		gtk_tree_model_get(GTK_TREE_MODEL(prefs_status_icon_themes), &iter, 2, &name, -1);
-
-		if(!name || !g_str_equal(name, ""))
-			theme = PIDGIN_STATUS_ICON_THEME(purple_theme_manager_find_theme(name, "status-icon"));
-
-		g_free(name);
-
-		pidgin_stock_load_status_icon_theme(theme);
-		pidgin_blist_refresh(purple_get_blist());
-	}
-}
-
 static GtkWidget *
 interface_page(void)
 {
@@ -1465,24 +1350,6 @@
 
 	sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
 
-	/* Buddy List Themes */
-	vbox = pidgin_make_frame(ret, _("Buddy List Theme"));
-
-	prefs_blist_themes_combo_box = prefs_build_theme_combo_box(prefs_blist_themes,
-						purple_prefs_get_string(PIDGIN_PREFS_ROOT "/blist/theme"),
-						"blist");
-
-	gtk_box_pack_start(GTK_BOX (vbox), prefs_blist_themes_combo_box, FALSE, FALSE, 0);
-	g_signal_connect(G_OBJECT(prefs_blist_themes_combo_box), "changed", (GCallback)prefs_set_blist_theme_cb, NULL);
-
-	/* Status Icon Themes */
-	prefs_status_themes_combo_box = prefs_build_theme_combo_box(prefs_status_icon_themes,
-						purple_prefs_get_string(PIDGIN_PREFS_ROOT "/status/icon-theme"),
-						"icon");
-
-	gtk_box_pack_start(GTK_BOX (vbox), prefs_status_themes_combo_box, FALSE, FALSE, 0);
-	g_signal_connect(G_OBJECT(prefs_status_themes_combo_box), "changed", (GCallback)prefs_set_status_icon_theme_cb, NULL);
-
 	/* System Tray */
 	vbox = pidgin_make_frame(ret, _("System Tray Icon"));
 	label = pidgin_prefs_dropdown(vbox, _("_Show system tray icon:"), PURPLE_PREF_STRING,
@@ -1561,12 +1428,13 @@
 	return ret;
 }
 
-#if GTK_CHECK_VERSION(2,4,0)
+#ifdef _WIN32
 static void
 pidgin_custom_font_set(GtkFontButton *font_button, gpointer nul)
 {
 	purple_prefs_set_string(PIDGIN_PREFS_ROOT "/conversations/custom_font",
-				gtk_font_button_get_font_name(font_button));
+				gtk_font_button_get_font_name(font_button))
+;
 }
 #endif
 
@@ -1578,16 +1446,9 @@
 	GtkWidget *toolbar;
 	GtkWidget *iconpref1;
 	GtkWidget *iconpref2;
-	GtkWidget *fontpref;
 	GtkWidget *imhtml;
 	GtkWidget *frame;
 
-#if GTK_CHECK_VERSION(2,4,0)
-	GtkWidget *hbox;
-	GtkWidget *font_button;
-	const char *font_name;
-#endif
-
 	ret = gtk_vbox_new(FALSE, PIDGIN_HIG_CAT_SPACE);
 	gtk_container_set_border_width(GTK_CONTAINER(ret), PIDGIN_HIG_BORDER);
 
@@ -1625,12 +1486,14 @@
 		PIDGIN_PREFS_ROOT "/conversations/minimum_entry_lines",
 		1, 8, NULL);
 
-#if GTK_CHECK_VERSION(2,4,0)
+#if GTK_CHECK_VERSION(2,4,0) && defined _WIN32
+	{
+	GtkWidget *fontpref, *font_button, *hbox;
+	const char *font_name;
 	vbox = pidgin_make_frame(ret, _("Font"));
-	if (purple_running_gnome())
-		fontpref = pidgin_prefs_checkbox(_("Use document font from _theme"), PIDGIN_PREFS_ROOT "/conversations/use_theme_font", vbox);
-	else
-		fontpref = pidgin_prefs_checkbox(_("Use font from _theme"), PIDGIN_PREFS_ROOT "/conversations/use_theme_font", vbox);
+
+	fontpref = pidgin_prefs_checkbox(_("Use font from _theme"),
+									 PIDGIN_PREFS_ROOT "/conversations/use_theme_font", vbox);
 
 	font_name = purple_prefs_get_string(PIDGIN_PREFS_ROOT "/conversations/custom_font");
 	if ((font_name == NULL) || (*font_name == '\0')) {
@@ -1645,15 +1508,16 @@
 		gtk_widget_set_sensitive(hbox, FALSE);
 	g_signal_connect(G_OBJECT(fontpref), "clicked", G_CALLBACK(pidgin_toggle_sensitive), hbox);
 	g_signal_connect(G_OBJECT(font_button), "font-set", G_CALLBACK(pidgin_custom_font_set), NULL);
+
+	}
 #endif
 
 	vbox = pidgin_make_frame(ret, _("Default Formatting"));
-	gtk_box_set_child_packing(GTK_BOX(vbox->parent), vbox, TRUE, TRUE, 0, GTK_PACK_START);
 
 	frame = pidgin_create_imhtml(TRUE, &imhtml, &toolbar, NULL);
 	gtk_widget_show(frame);
 	gtk_widget_set_name(imhtml, "pidgin_prefs_font_imhtml");
-	gtk_widget_set_size_request(frame, 300, -1);
+	gtk_widget_set_size_request(frame, 450, -1);
 	gtk_imhtml_set_whole_buffer_formatting_only(GTK_IMHTML(imhtml), TRUE);
 	gtk_imhtml_set_format_functions(GTK_IMHTML(imhtml),
 									GTK_IMHTML_BOLD |
@@ -1761,17 +1625,18 @@
 }
 
 static void
-proxy_button_clicked_cb(GtkWidget *button, gpointer null)
+proxy_button_clicked_cb(GtkWidget *button, gchar *program)
 {
 	GError *err = NULL;
 
-	if (g_spawn_command_line_async ("gnome-network-preferences", &err))
+	if (g_spawn_command_line_async(program, &err))
 		return;
 
 	purple_notify_error(NULL, NULL, _("Cannot start proxy configuration program."), err->message);
 	g_error_free(err);
 }
 
+#ifndef _WIN32
 static void
 browser_button_clicked_cb(GtkWidget *button, gpointer null)
 {
@@ -1783,6 +1648,7 @@
 	purple_notify_error(NULL, NULL, _("Cannot start browser configuration program."), err->message);
 	g_error_free(err);
 }
+#endif
 
 static void
 auto_ip_button_clicked_cb(GtkWidget *button, gpointer null)
@@ -1826,12 +1692,8 @@
 {
 	GtkWidget *ret;
 	GtkWidget *vbox, *hbox, *entry;
-	GtkWidget *table = NULL;
 	GtkWidget *label, *auto_ip_checkbox, *ports_checkbox, *spin_button;
-	GtkWidget *proxy_warning = NULL, *browser_warning = NULL;
-	GtkWidget *proxy_button = NULL, *browser_button = NULL;
 	GtkSizeGroup *sg;
-	PurpleProxyInfo *proxy_info = NULL;
 
 	ret = gtk_vbox_new(FALSE, PIDGIN_HIG_CAT_SPACE);
 	gtk_container_set_border_width (GTK_CONTAINER (ret), PIDGIN_HIG_BORDER);
@@ -1935,180 +1797,8 @@
 	pidgin_prefs_labeled_password(hbox, _("Pass_word:"),
 		"/purple/network/turn_password", NULL);
 
-	if (purple_running_gnome()) {
-		vbox = pidgin_make_frame(ret, _("Proxy Server &amp; Browser"));
-		prefs_proxy_frame = gtk_vbox_new(FALSE, 0);
-
-		proxy_warning = hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
-		gtk_container_add(GTK_CONTAINER(vbox), hbox);
-
-		label = gtk_label_new(NULL);
-		gtk_label_set_markup(GTK_LABEL(label),
-		                     _("<b>Proxy configuration program was not found.</b>"));
-		gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
-
-		browser_warning = hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
-		gtk_container_add(GTK_CONTAINER(vbox), hbox);
-
-		label = gtk_label_new(NULL);
-		gtk_label_set_markup(GTK_LABEL(label),
-		                     _("<b>Browser configuration program was not found.</b>"));
-		gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
-
-		hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
-		gtk_container_add(GTK_CONTAINER(vbox), hbox);
-		label = gtk_label_new(_("Proxy & Browser preferences are configured\n"
-		                        "in GNOME Preferences"));
-		gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
-		gtk_widget_show(label);
-
-		hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
-		gtk_container_add(GTK_CONTAINER(vbox), hbox);
-		proxy_button = gtk_button_new_with_mnemonic(_("Configure _Proxy"));
-		g_signal_connect(G_OBJECT(proxy_button), "clicked",
-		                 G_CALLBACK(proxy_button_clicked_cb), NULL);
-		gtk_box_pack_start(GTK_BOX(hbox), proxy_button, FALSE, FALSE, 0);
-		gtk_widget_show(proxy_button);
-		browser_button = gtk_button_new_with_mnemonic(_("Configure _Browser"));
-		g_signal_connect(G_OBJECT(browser_button), "clicked",
-		                 G_CALLBACK(browser_button_clicked_cb), NULL);
-		gtk_box_pack_start(GTK_BOX(hbox), browser_button, FALSE, FALSE, 0);
-		gtk_widget_show(browser_button);
-	} else {
-		vbox = pidgin_make_frame(ret, _("Proxy Server"));
-		prefs_proxy_frame = gtk_vbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
-		prefs_proxy_subframe = gtk_vbox_new(FALSE, 0);
-
-		/* This is a global option that affects SOCKS4 usage even with account-specific proxy settings */
-		pidgin_prefs_checkbox(_("Use remote _DNS with SOCKS4 proxies"),
-							  "/purple/proxy/socks4_remotedns", prefs_proxy_frame);
-		gtk_box_pack_start(GTK_BOX(vbox), prefs_proxy_frame, 0, 0, 0);
-
-		pidgin_prefs_dropdown(prefs_proxy_frame, _("Proxy t_ype:"), PURPLE_PREF_STRING,
-					"/purple/proxy/type",
-					_("No proxy"), "none",
-					"SOCKS 4", "socks4",
-					"SOCKS 5", "socks5",
-					"HTTP", "http",
-					_("Use Environmental Settings"), "envvar",
-					NULL);
-		gtk_box_pack_start(GTK_BOX(prefs_proxy_frame), prefs_proxy_subframe, 0, 0, 0);
-		proxy_info = purple_global_proxy_get_info();
-
-		purple_prefs_connect_callback(prefs, "/purple/proxy/type",
-					    proxy_changed_cb, prefs_proxy_subframe);
-
-		table = gtk_table_new(4, 2, FALSE);
-		gtk_container_set_border_width(GTK_CONTAINER(table), 0);
-		gtk_table_set_col_spacings(GTK_TABLE(table), 5);
-		gtk_table_set_row_spacings(GTK_TABLE(table), 10);
-		gtk_container_add(GTK_CONTAINER(prefs_proxy_subframe), table);
-
-
-		label = gtk_label_new_with_mnemonic(_("_Host:"));
-		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
-		gtk_table_attach(GTK_TABLE(table), label, 0, 1, 0, 1, GTK_FILL, 0, 0, 0);
-
-		entry = gtk_entry_new();
-		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
-		gtk_table_attach(GTK_TABLE(table), entry, 1, 2, 0, 1, GTK_FILL, 0, 0, 0);
-		g_signal_connect(G_OBJECT(entry), "changed",
-				 G_CALLBACK(proxy_print_option), (void *)PROXYHOST);
-
-		if (proxy_info != NULL && purple_proxy_info_get_host(proxy_info))
-			gtk_entry_set_text(GTK_ENTRY(entry),
-					   purple_proxy_info_get_host(proxy_info));
-
-		hbox = gtk_hbox_new(TRUE, 5);
-		gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
-		pidgin_set_accessible_label (entry, label);
-
-		label = gtk_label_new_with_mnemonic(_("P_ort:"));
-		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
-		gtk_table_attach(GTK_TABLE(table), label, 2, 3, 0, 1, GTK_FILL, 0, 0, 0);
-
-		entry = gtk_spin_button_new_with_range(0, 65535, 1);
-		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
-		gtk_table_attach(GTK_TABLE(table), entry, 3, 4, 0, 1, GTK_FILL, 0, 0, 0);
-		g_signal_connect(G_OBJECT(entry), "changed",
-				 G_CALLBACK(proxy_print_option), (void *)PROXYPORT);
-
-		if (proxy_info != NULL && purple_proxy_info_get_port(proxy_info) != 0) {
-			char buf[128];
-			g_snprintf(buf, sizeof(buf), "%d",
-				   purple_proxy_info_get_port(proxy_info));
-
-			gtk_entry_set_text(GTK_ENTRY(entry), buf);
-		}
-		pidgin_set_accessible_label (entry, label);
-
-		label = gtk_label_new_with_mnemonic(_("User_name:"));
-		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
-		gtk_table_attach(GTK_TABLE(table), label, 0, 1, 1, 2, GTK_FILL, 0, 0, 0);
-
-		entry = gtk_entry_new();
-		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
-		gtk_table_attach(GTK_TABLE(table), entry, 1, 2, 1, 2, GTK_FILL, 0, 0, 0);
-		g_signal_connect(G_OBJECT(entry), "changed",
-				 G_CALLBACK(proxy_print_option), (void *)PROXYUSER);
-
-		if (proxy_info != NULL && purple_proxy_info_get_username(proxy_info) != NULL)
-			gtk_entry_set_text(GTK_ENTRY(entry),
-						   purple_proxy_info_get_username(proxy_info));
-
-		hbox = gtk_hbox_new(TRUE, 5);
-		gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
-		pidgin_set_accessible_label (entry, label);
-
-		label = gtk_label_new_with_mnemonic(_("Pa_ssword:"));
-		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
-		gtk_table_attach(GTK_TABLE(table), label, 2, 3, 1, 2, GTK_FILL, 0, 0, 0);
-
-		entry = gtk_entry_new();
-		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
-		gtk_table_attach(GTK_TABLE(table), entry, 3, 4, 1, 2, GTK_FILL , 0, 0, 0);
-		gtk_entry_set_visibility(GTK_ENTRY(entry), FALSE);
-#if !GTK_CHECK_VERSION(2,16,0)
-		if (gtk_entry_get_invisible_char(GTK_ENTRY(entry)) == '*')
-			gtk_entry_set_invisible_char(GTK_ENTRY(entry), PIDGIN_INVISIBLE_CHAR);
-#endif /* Less than GTK+ 2.16 */
-		g_signal_connect(G_OBJECT(entry), "changed",
-				 G_CALLBACK(proxy_print_option), (void *)PROXYPASS);
-
-		if (proxy_info != NULL && purple_proxy_info_get_password(proxy_info) != NULL)
-			gtk_entry_set_text(GTK_ENTRY(entry),
-					   purple_proxy_info_get_password(proxy_info));
-		pidgin_set_accessible_label (entry, label);
-	}
-
 	gtk_widget_show_all(ret);
 	g_object_unref(sg);
-	/* Only hide table if not running gnome otherwise we hide the IP address table! */
-	if (!purple_running_gnome() && (proxy_info == NULL ||
-	    purple_proxy_info_get_type(proxy_info) == PURPLE_PROXY_NONE ||
-	    purple_proxy_info_get_type(proxy_info) == PURPLE_PROXY_USE_ENVVAR)) {
-		gtk_widget_hide(table);
-	} else if (purple_running_gnome()) {
-		gchar *path;
-		path = g_find_program_in_path("gnome-network-preferences");
-		if (path != NULL) {
-			gtk_widget_set_sensitive(proxy_button, TRUE);
-			gtk_widget_hide(proxy_warning);
-			g_free(path);
-		} else {
-			gtk_widget_set_sensitive(proxy_button, FALSE);
-			gtk_widget_show(proxy_warning);
-		}
-		path = g_find_program_in_path("gnome-default-applications-properties");
-		if (path != NULL) {
-			gtk_widget_set_sensitive(browser_button, TRUE);
-			gtk_widget_hide(browser_warning);
-			g_free(path);
-		} else {
-			gtk_widget_set_sensitive(browser_button, FALSE);
-			gtk_widget_show(browser_warning);
-		}
-	}
 
 	return ret;
 }
@@ -2203,65 +1893,246 @@
 static GtkWidget *
 browser_page(void)
 {
-	GtkWidget *ret;
-	GtkWidget *vbox;
-	GtkWidget *hbox;
-	GtkWidget *label;
-	GtkWidget *entry;
+	GtkWidget *ret, *vbox, *hbox, *label, *entry, *browser_button;
 	GtkSizeGroup *sg;
 	GList *browsers = NULL;
 
 	ret = gtk_vbox_new(FALSE, PIDGIN_HIG_CAT_SPACE);
 	gtk_container_set_border_width (GTK_CONTAINER (ret), PIDGIN_HIG_BORDER);
 
-	sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
 	vbox = pidgin_make_frame (ret, _("Browser Selection"));
 
-	browsers = get_available_browsers();
-	if (browsers != NULL) {
-		label = pidgin_prefs_dropdown_from_list(vbox,_("_Browser:"), PURPLE_PREF_STRING,
-										 PIDGIN_PREFS_ROOT "/browsers/browser",
-										 browsers);
-		g_list_free(browsers);
-		gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
-		gtk_size_group_add_widget(sg, label);
-
-		hbox = gtk_hbox_new(FALSE, 0);
-		label = pidgin_prefs_dropdown(hbox, _("_Open link in:"), PURPLE_PREF_INT,
-			PIDGIN_PREFS_ROOT "/browsers/place",
-			_("Browser default"), PIDGIN_BROWSER_DEFAULT,
-			_("Existing window"), PIDGIN_BROWSER_CURRENT,
-			_("New window"), PIDGIN_BROWSER_NEW_WINDOW,
-			_("New tab"), PIDGIN_BROWSER_NEW_TAB,
-			NULL);
-		gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
-		gtk_size_group_add_widget(sg, label);
-		gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
-
-		if (!strcmp(purple_prefs_get_string(PIDGIN_PREFS_ROOT "/browsers/browser"), "custom"))
+	if(purple_running_gnome()) {
+		gchar *path = g_find_program_in_path("gnome-default-applications-properties");
+
+		hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+		label = gtk_label_new(_("Browser preferences are configured in GNOME preferences"));
+		gtk_container_add(GTK_CONTAINER(vbox), hbox);
+		gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
+
+		hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+		gtk_container_add(GTK_CONTAINER(vbox), hbox);
+
+		if(path == NULL) {
+			label = gtk_label_new(NULL);
+			gtk_label_set_markup(GTK_LABEL(label),
+								 _("<b>Browser configuration program was not found.</b>"));
+			gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
+		} else {
+			browser_button = gtk_button_new_with_mnemonic(_("Configure _Browser"));
+			g_signal_connect(G_OBJECT(browser_button), "clicked",
+							 G_CALLBACK(browser_button_clicked_cb), NULL);
+			gtk_box_pack_start(GTK_BOX(hbox), browser_button, FALSE, FALSE, 0);
+		}
+
+		g_free(path);
+		gtk_widget_show_all(ret);
+	} else {
+		sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
+	
+		browsers = get_available_browsers();
+		if (browsers != NULL) {
+			label = pidgin_prefs_dropdown_from_list(vbox,_("_Browser:"), PURPLE_PREF_STRING,
+											 PIDGIN_PREFS_ROOT "/browsers/browser",
+											 browsers);
+			g_list_free(browsers);
+			gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
+			gtk_size_group_add_widget(sg, label);
+	
+			hbox = gtk_hbox_new(FALSE, 0);
+			label = pidgin_prefs_dropdown(hbox, _("_Open link in:"), PURPLE_PREF_INT,
+				PIDGIN_PREFS_ROOT "/browsers/place",
+				_("Browser default"), PIDGIN_BROWSER_DEFAULT,
+				_("Existing window"), PIDGIN_BROWSER_CURRENT,
+				_("New window"), PIDGIN_BROWSER_NEW_WINDOW,
+				_("New tab"), PIDGIN_BROWSER_NEW_TAB,
+				NULL);
+			gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
+			gtk_size_group_add_widget(sg, label);
+			gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
+	
+			if (!strcmp(purple_prefs_get_string(PIDGIN_PREFS_ROOT "/browsers/browser"), "custom"))
+				gtk_widget_set_sensitive(hbox, FALSE);
+			purple_prefs_connect_callback(prefs, PIDGIN_PREFS_ROOT "/browsers/browser",
+										browser_changed1_cb, hbox);
+		}
+
+		entry = gtk_entry_new();
+		gtk_entry_set_text(GTK_ENTRY(entry),
+						   purple_prefs_get_path(PIDGIN_PREFS_ROOT "/browsers/command"));
+		g_signal_connect(G_OBJECT(entry), "focus-out-event",
+						 G_CALLBACK(manual_browser_set), NULL);
+		hbox = pidgin_add_widget_to_vbox(GTK_BOX(vbox), _("_Manual:\n(%s for URL)"), sg, entry, TRUE, NULL);
+		if (strcmp(purple_prefs_get_string(PIDGIN_PREFS_ROOT "/browsers/browser"), "custom"))
 			gtk_widget_set_sensitive(hbox, FALSE);
 		purple_prefs_connect_callback(prefs, PIDGIN_PREFS_ROOT "/browsers/browser",
-									browser_changed1_cb, hbox);
+				browser_changed2_cb, hbox);
+	
+		gtk_widget_show_all(ret);
+		g_object_unref(sg);
 	}
 
-	entry = gtk_entry_new();
-	gtk_entry_set_text(GTK_ENTRY(entry),
-					   purple_prefs_get_path(PIDGIN_PREFS_ROOT "/browsers/command"));
-	g_signal_connect(G_OBJECT(entry), "focus-out-event",
-					 G_CALLBACK(manual_browser_set), NULL);
-	hbox = pidgin_add_widget_to_vbox(GTK_BOX(vbox), _("_Manual:\n(%s for URL)"), sg, entry, TRUE, NULL);
-	if (strcmp(purple_prefs_get_string(PIDGIN_PREFS_ROOT "/browsers/browser"), "custom"))
-		gtk_widget_set_sensitive(hbox, FALSE);
-	purple_prefs_connect_callback(prefs, PIDGIN_PREFS_ROOT "/browsers/browser",
-			browser_changed2_cb, hbox);
-
-	gtk_widget_show_all(ret);
-	g_object_unref(sg);
 	return ret;
 }
 #endif /*_WIN32*/
 
 static GtkWidget *
+proxy_page(void)
+{
+	GtkWidget *ret = NULL, *vbox = NULL, *hbox = NULL;
+	GtkWidget *table = NULL, *entry = NULL, *label = NULL, *proxy_button = NULL;
+	GtkWidget *prefs_proxy_frame = NULL;
+	PurpleProxyInfo *proxy_info;
+
+	ret = gtk_vbox_new(FALSE, PIDGIN_HIG_CAT_SPACE);
+	gtk_container_set_border_width(GTK_CONTAINER(ret), PIDGIN_HIG_BORDER);
+	vbox = pidgin_make_frame(ret, _("Proxy Server"));
+	prefs_proxy_frame = gtk_vbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+
+	if(purple_running_gnome()) {
+		gchar *path = NULL;
+
+		hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+		label = gtk_label_new(_("Proxy preferences are configured in GNOME preferences"));
+		gtk_container_add(GTK_CONTAINER(vbox), hbox);
+		gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
+
+		hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+		gtk_container_add(GTK_CONTAINER(vbox), hbox);
+
+		path = g_find_program_in_path("gnome-network-properties");
+		if (path == NULL)
+			path = g_find_program_in_path("gnome-network-preferences");
+
+		if (path == NULL) {
+			label = gtk_label_new(NULL);
+			gtk_label_set_markup(GTK_LABEL(label),
+								 _("<b>Proxy configuration program was not found.</b>"));
+			gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
+		} else {
+			proxy_button = gtk_button_new_with_mnemonic(_("Configure _Proxy"));
+			g_signal_connect(G_OBJECT(proxy_button), "clicked",
+							 G_CALLBACK(proxy_button_clicked_cb),
+							 path);
+			gtk_box_pack_start(GTK_BOX(hbox), proxy_button, FALSE, FALSE, 0);
+		}
+
+		/* NOTE: path leaks, but only when the prefs window is destroyed,
+		         which is never */
+		gtk_widget_show_all(ret);
+	} else {
+		GtkWidget *prefs_proxy_subframe = gtk_vbox_new(FALSE, 0);
+
+		/* This is a global option that affects SOCKS4 usage even with
+		 * account-specific proxy settings */
+		pidgin_prefs_checkbox(_("Use remote _DNS with SOCKS4 proxies"),
+							  "/purple/proxy/socks4_remotedns", prefs_proxy_frame);
+		gtk_box_pack_start(GTK_BOX(vbox), prefs_proxy_frame, 0, 0, 0);
+
+		pidgin_prefs_dropdown(prefs_proxy_frame, _("Proxy t_ype:"), PURPLE_PREF_STRING,
+					"/purple/proxy/type",
+					_("No proxy"), "none",
+					"SOCKS 4", "socks4",
+					"SOCKS 5", "socks5",
+					"HTTP", "http",
+					_("Use Environmental Settings"), "envvar",
+					NULL);
+		gtk_box_pack_start(GTK_BOX(prefs_proxy_frame), prefs_proxy_subframe, 0, 0, 0);
+		proxy_info = purple_global_proxy_get_info();
+
+		gtk_widget_show_all(ret);
+
+		purple_prefs_connect_callback(prefs, "/purple/proxy/type",
+					    proxy_changed_cb, prefs_proxy_subframe);
+
+		table = gtk_table_new(4, 2, FALSE);
+		gtk_container_set_border_width(GTK_CONTAINER(table), 0);
+		gtk_table_set_col_spacings(GTK_TABLE(table), 5);
+		gtk_table_set_row_spacings(GTK_TABLE(table), 10);
+		gtk_container_add(GTK_CONTAINER(prefs_proxy_subframe), table);
+
+		label = gtk_label_new_with_mnemonic(_("_Host:"));
+		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
+		gtk_table_attach(GTK_TABLE(table), label, 0, 1, 0, 1, GTK_FILL, 0, 0, 0);
+
+		entry = gtk_entry_new();
+		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
+		gtk_table_attach(GTK_TABLE(table), entry, 1, 2, 0, 1, GTK_FILL, 0, 0, 0);
+		g_signal_connect(G_OBJECT(entry), "changed",
+				 G_CALLBACK(proxy_print_option), (void *)PROXYHOST);
+
+		if (proxy_info != NULL && purple_proxy_info_get_host(proxy_info))
+			gtk_entry_set_text(GTK_ENTRY(entry),
+					   purple_proxy_info_get_host(proxy_info));
+
+		hbox = gtk_hbox_new(TRUE, 5);
+		gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
+		pidgin_set_accessible_label (entry, label);
+
+		label = gtk_label_new_with_mnemonic(_("P_ort:"));
+		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
+		gtk_table_attach(GTK_TABLE(table), label, 2, 3, 0, 1, GTK_FILL, 0, 0, 0);
+
+		entry = gtk_spin_button_new_with_range(0, 65535, 1);
+		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
+		gtk_table_attach(GTK_TABLE(table), entry, 3, 4, 0, 1, GTK_FILL, 0, 0, 0);
+		g_signal_connect(G_OBJECT(entry), "changed",
+				 G_CALLBACK(proxy_print_option), (void *)PROXYPORT);
+
+		if (proxy_info != NULL && purple_proxy_info_get_port(proxy_info) != 0) {
+			gtk_spin_button_set_value(GTK_SPIN_BUTTON(entry),
+				purple_proxy_info_get_port(proxy_info));
+		}
+		pidgin_set_accessible_label (entry, label);
+
+		label = gtk_label_new_with_mnemonic(_("User_name:"));
+		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
+		gtk_table_attach(GTK_TABLE(table), label, 0, 1, 1, 2, GTK_FILL, 0, 0, 0);
+
+		entry = gtk_entry_new();
+		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
+		gtk_table_attach(GTK_TABLE(table), entry, 1, 2, 1, 2, GTK_FILL, 0, 0, 0);
+		g_signal_connect(G_OBJECT(entry), "changed",
+				 G_CALLBACK(proxy_print_option), (void *)PROXYUSER);
+
+		if (proxy_info != NULL && purple_proxy_info_get_username(proxy_info) != NULL)
+			gtk_entry_set_text(GTK_ENTRY(entry),
+						   purple_proxy_info_get_username(proxy_info));
+
+		hbox = gtk_hbox_new(TRUE, 5);
+		gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
+		pidgin_set_accessible_label (entry, label);
+
+		label = gtk_label_new_with_mnemonic(_("Pa_ssword:"));
+		gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
+		gtk_table_attach(GTK_TABLE(table), label, 2, 3, 1, 2, GTK_FILL, 0, 0, 0);
+
+		entry = gtk_entry_new();
+		gtk_label_set_mnemonic_widget(GTK_LABEL(label), entry);
+		gtk_table_attach(GTK_TABLE(table), entry, 3, 4, 1, 2, GTK_FILL , 0, 0, 0);
+		gtk_entry_set_visibility(GTK_ENTRY(entry), FALSE);
+#if !GTK_CHECK_VERSION(2,16,0)
+		if (gtk_entry_get_invisible_char(GTK_ENTRY(entry)) == '*')
+			gtk_entry_set_invisible_char(GTK_ENTRY(entry), PIDGIN_INVISIBLE_CHAR);
+#endif /* Less than GTK+ 2.16 */
+		g_signal_connect(G_OBJECT(entry), "changed",
+				 G_CALLBACK(proxy_print_option), (void *)PROXYPASS);
+
+		if (proxy_info != NULL && purple_proxy_info_get_password(proxy_info) != NULL)
+			gtk_entry_set_text(GTK_ENTRY(entry),
+					   purple_proxy_info_get_password(proxy_info));
+		pidgin_set_accessible_label (entry, label);
+
+		proxy_changed_cb("/purple/proxy/type", PURPLE_PREF_STRING,
+			purple_prefs_get_string("/purple/proxy/type"),
+			prefs_proxy_subframe);
+
+	}
+
+	return ret;
+}
+
+static GtkWidget *
 logging_page(void)
 {
 	GtkWidget *ret;
@@ -2524,7 +2395,7 @@
 sound_page(void)
 {
 	GtkWidget *ret;
-	GtkWidget *vbox, *sw, *button;
+	GtkWidget *vbox, *vbox2, *sw, *button;
 	GtkSizeGroup *sg;
 	GtkTreeIter iter;
 	GtkWidget *event_view;
@@ -2548,9 +2419,13 @@
 
 	sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
 
+	vbox2 = pidgin_make_frame(ret, _("Sound Options"));
+
+	vbox = gtk_vbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+	gtk_box_pack_start(GTK_BOX(vbox2), vbox, FALSE, FALSE, 0);
+
 #ifndef _WIN32
-	vbox = pidgin_make_frame (ret, _("Sound Method"));
-	dd = pidgin_prefs_dropdown(vbox, _("_Method:"), PURPLE_PREF_STRING,
+	dd = pidgin_prefs_dropdown(vbox2, _("_Method:"), PURPLE_PREF_STRING,
 			PIDGIN_PREFS_ROOT "/sound/method",
 			_("Console beep"), "beep",
 #ifdef USE_GSTREAMER
@@ -2580,8 +2455,6 @@
 					"custom"));
 #endif /* _WIN32 */
 
-	vbox = pidgin_make_frame (ret, _("Sound Options"));
-
 	button = pidgin_prefs_checkbox(_("M_ute sounds"), PIDGIN_PREFS_ROOT "/sound/mute", vbox);
 	purple_prefs_connect_callback(prefs, PIDGIN_PREFS_ROOT "/sound/mute", mute_changed_cb, button);
 
@@ -2629,16 +2502,6 @@
 	gtk_box_set_child_packing(GTK_BOX(vbox->parent->parent->parent),
 			vbox->parent->parent, TRUE, TRUE, 0, GTK_PACK_START);
 
-	/* SOUND THEMES */
-	prefs_sound_themes_combo_box = prefs_build_theme_combo_box(prefs_sound_themes,
-						purple_prefs_get_string(PIDGIN_PREFS_ROOT "/sound/theme"),
-						"sound");
-
-
-	gtk_box_pack_start(GTK_BOX (vbox), prefs_sound_themes_combo_box, FALSE, FALSE, 0);
-
-	g_signal_connect(G_OBJECT(prefs_sound_themes_combo_box), "changed", (GCallback)prefs_set_sound_theme_cb, NULL);
-
 	/* SOUND SELECTION */
 	sw = gtk_scrolled_window_new(NULL,NULL);
 	gtk_widget_set_size_request(sw, -1, 100);
@@ -2743,6 +2606,7 @@
 {
 	GtkWidget *ret;
 	GtkWidget *vbox;
+	GtkWidget *hbox;
 	GtkWidget *dd;
 	GtkWidget *label;
 	GtkWidget *button;
@@ -2769,6 +2633,28 @@
 	gtk_size_group_add_widget(sg, dd);
 	gtk_misc_set_alignment(GTK_MISC(dd), 0, 0.5);
 
+	select = pidgin_prefs_labeled_spin_button(vbox,
+			_("_Minutes before becoming idle:"), "/purple/away/mins_before_away",
+			1, 24 * 60, sg);
+
+	hbox = gtk_hbox_new(FALSE, PIDGIN_HIG_BOX_SPACE);
+	gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
+
+	button = pidgin_prefs_checkbox(_("Change to this status when _idle:"),
+						   "/purple/away/away_when_idle", hbox);
+	gtk_size_group_add_widget(sg, button);
+
+	/* TODO: Show something useful if we don't have any saved statuses. */
+	menu = pidgin_status_menu(purple_savedstatus_get_idleaway(), G_CALLBACK(set_idle_away));
+	gtk_size_group_add_widget(sg, menu);
+	gtk_box_pack_start(GTK_BOX(hbox), menu, FALSE, FALSE, 0);
+
+	g_signal_connect(G_OBJECT(button), "clicked",
+			 G_CALLBACK(pidgin_toggle_sensitive), menu);
+
+	if(!purple_prefs_get_bool("/purple/away/away_when_idle"))
+		gtk_widget_set_sensitive(GTK_WIDGET(menu), FALSE);
+
 	/* Away stuff */
 	vbox = pidgin_make_frame(ret, _("Away"));
 
@@ -2781,44 +2667,23 @@
 	gtk_size_group_add_widget(sg, dd);
 	gtk_misc_set_alignment(GTK_MISC(dd), 0, 0.5);
 
-	/* Auto-away stuff */
-	vbox = pidgin_make_frame(ret, _("Auto-away"));
-
-	select = pidgin_prefs_labeled_spin_button(vbox,
-			_("_Minutes before becoming idle:"), "/purple/away/mins_before_away",
-			1, 24 * 60, sg);
-
-	button = pidgin_prefs_checkbox(_("Change status when _idle"),
-						   "/purple/away/away_when_idle", vbox);
-
-	/* TODO: Show something useful if we don't have any saved statuses. */
-	menu = pidgin_status_menu(purple_savedstatus_get_idleaway(), G_CALLBACK(set_idle_away));
-	pidgin_add_widget_to_vbox(GTK_BOX(vbox), _("Change _status to:"), sg, menu, TRUE, &label);
-	g_signal_connect(G_OBJECT(button), "clicked",
-			 G_CALLBACK(pidgin_toggle_sensitive), menu);
-	g_signal_connect(G_OBJECT(button), "clicked",
-					 G_CALLBACK(pidgin_toggle_sensitive), label);
-
-	if (!purple_prefs_get_bool("/purple/away/away_when_idle")) {
-		gtk_widget_set_sensitive(GTK_WIDGET(menu), FALSE);
-		gtk_widget_set_sensitive(GTK_WIDGET(label), FALSE);
-	}
-
 	/* Signon status stuff */
 	vbox = pidgin_make_frame(ret, _("Status at Startup"));
 
 	button = pidgin_prefs_checkbox(_("Use status from last _exit at startup"),
 		"/purple/savedstatus/startup_current_status", vbox);
+	gtk_size_group_add_widget(sg, button);
 
 	/* TODO: Show something useful if we don't have any saved statuses. */
 	menu = pidgin_status_menu(purple_savedstatus_get_startup(), G_CALLBACK(set_startupstatus));
+	gtk_size_group_add_widget(sg, menu);
 	g_signal_connect(G_OBJECT(button), "clicked",
 			 G_CALLBACK(pidgin_toggle_sensitive), menu);
 	pidgin_add_widget_to_vbox(GTK_BOX(vbox), _("Status to a_pply at startup:"), sg, menu, TRUE, &label);
 	g_signal_connect(G_OBJECT(button), "clicked",
 					 G_CALLBACK(pidgin_toggle_sensitive), label);
 
-	if (purple_prefs_get_bool("/purple/savedstatus/startup_current_status")) {
+	if(purple_prefs_get_bool("/purple/savedstatus/startup_current_status")) {
 		gtk_widget_set_sensitive(GTK_WIDGET(menu), FALSE);
 		gtk_widget_set_sensitive(GTK_WIDGET(label), FALSE);
 	}
@@ -2844,19 +2709,22 @@
 prefs_notebook_init(void)
 {
 	prefs_notebook_add_page(_("Interface"), interface_page(), notebook_page++);
-	prefs_notebook_add_page(_("Conversations"), conv_page(), notebook_page++);
-	prefs_notebook_add_page(_("Smiley Themes"), theme_page(), notebook_page++);
-	prefs_notebook_add_page(_("Sounds"), sound_page(), notebook_page++);
-	prefs_notebook_add_page(_("Network"), network_page(), notebook_page++);
+
 #ifndef _WIN32
 	/* We use the registered default browser in windows */
-	/* if the user is running gnome 2.x or Mac OS X, hide the browsers tab */
-	if ((purple_running_gnome() == FALSE) && (purple_running_osx() == FALSE)) {
+	/* if the user is running Mac OS X, hide the browsers tab */
+	if(purple_running_osx() == FALSE)
 		prefs_notebook_add_page(_("Browser"), browser_page(), notebook_page++);
-	}
 #endif
+
+	prefs_notebook_add_page(_("Conversations"), conv_page(), notebook_page++);
 	prefs_notebook_add_page(_("Logging"), logging_page(), notebook_page++);
+	prefs_notebook_add_page(_("Network"), network_page(), notebook_page++);
+	prefs_notebook_add_page(_("Proxy"), proxy_page(), notebook_page++);
+
+	prefs_notebook_add_page(_("Sounds"), sound_page(), notebook_page++);
 	prefs_notebook_add_page(_("Status / Idle"), away_page(), notebook_page++);
+	prefs_notebook_add_page(_("Themes"), theme_page(), notebook_page++);
 }
 
 void
@@ -2886,7 +2754,8 @@
 
 	/* The notebook */
 	prefsnotebook = notebook = gtk_notebook_new ();
-	gtk_box_pack_start (GTK_BOX (vbox), notebook, FALSE, FALSE, 0);
+	gtk_notebook_set_tab_pos(GTK_NOTEBOOK(notebook), GTK_POS_LEFT);
+	gtk_box_pack_start(GTK_BOX (vbox), notebook, FALSE, FALSE, 0);
 	gtk_widget_show(prefsnotebook);
 
 	button = pidgin_dialog_add_button(GTK_DIALOG(prefs), GTK_STOCK_CLOSE, NULL, NULL);
--- a/pidgin/gtksavedstatuses.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/pidgin/gtksavedstatuses.c	Fri Nov 20 16:36:33 2009 +0900
@@ -1862,6 +1862,9 @@
 	g_object_set(G_OBJECT(icon_rend),
 			"stock-size", gtk_icon_size_from_name(PIDGIN_ICON_SIZE_TANGO_EXTRA_SMALL),
 			NULL);
+#if GTK_CHECK_VERSION(2,6,0)
+	g_object_set(text_rend, "ellipsize", PANGO_ELLIPSIZE_END, NULL);
+#endif
 
 	gtk_combo_box_set_active(GTK_COMBO_BOX(combobox), index);
 	g_signal_connect(G_OBJECT(combobox), "changed", G_CALLBACK(status_menu_cb), callback);
--- a/pidgin/gtkutils.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/pidgin/gtkutils.c	Fri Nov 20 16:36:33 2009 +0900
@@ -113,26 +113,12 @@
 
 	gtk_imhtml_set_funcs(GTK_IMHTML(imhtml), &gtkimhtml_cbs);
 
+#ifdef _WIN32
 	if (!purple_prefs_get_bool(PIDGIN_PREFS_ROOT "/conversations/use_theme_font")) {
 		const char *font = purple_prefs_get_string(PIDGIN_PREFS_ROOT "/conversations/custom_font");
 		desc = pango_font_description_from_string(font);
-	} else if (purple_running_gnome()) {
-		/* Use the GNOME "document" font, if applicable */
-		char *path;
-
-		if ((path = g_find_program_in_path("gconftool-2"))) {
-			char *font = NULL;
-			char *err = NULL;
-			g_free(path);
-			if (g_spawn_command_line_sync(
-					"gconftool-2 -g /desktop/gnome/interface/document_font_name",
-					&font, &err, NULL, NULL)) {
-				desc = pango_font_description_from_string(font);
-			}
-			g_free(err);
-			g_free(font);
-		}
 	}
+#endif
 
 	if (desc) {
 		gtk_widget_modify_font(imhtml, desc);
--- a/pidgin/plugins/pidginrc.c	Tue Nov 17 11:40:49 2009 +0900
+++ b/pidgin/plugins/pidginrc.c	Fri Nov 20 16:36:33 2009 +0900
@@ -75,16 +75,19 @@
 
 static const gchar *font_prefs[] = {
 	"/plugins/gtk/purplerc/font/*pidgin_conv_entry",
+	"/plugins/gtk/purplerc/font/*pidgin_conv_imhtml",
 	"/plugins/gtk/purplerc/font/*pidgin_request_imhtml",
 	"/plugins/gtk/purplerc/font/*pidgin_notify_imhtml",
 };
 static const gchar *font_prefs_set[] = {
 	"/plugins/gtk/purplerc/set/font/*pidgin_conv_entry",
+	"/plugins/gtk/purplerc/set/font/*pidgin_conv_imhtml",
 	"/plugins/gtk/purplerc/set/font/*pidgin_request_imhtml",
 	"/plugins/gtk/purplerc/set/font/*pidgin_notify_imhtml",
 };
 static const gchar *font_names[] = {
 	N_("Conversation Entry"),
+	N_("Conversation History"),
 	N_("Request Dialog"),
 	N_("Notify Dialog")
 };
--- a/pidgin/win32/nsis/pidgin-installer.nsi	Tue Nov 17 11:40:49 2009 +0900
+++ b/pidgin/win32/nsis/pidgin-installer.nsi	Fri Nov 20 16:36:33 2009 +0900
@@ -750,6 +750,7 @@
     Delete "$INSTDIR\plugins\libicq.dll"
     Delete "$INSTDIR\plugins\libirc.dll"
     Delete "$INSTDIR\plugins\libmsn.dll"
+    Delete "$INSTDIR\plugins\libmxit.dll"
     Delete "$INSTDIR\plugins\libmyspace.dll"
     Delete "$INSTDIR\plugins\libnapster.dll"
     Delete "$INSTDIR\plugins\libnovell.dll"