changeset 1938:1d9c1026d9f8 trunk

[svn] - DoubleSize support. This has bugs, the most notable one being that DoubleSize only works right if you restart the player. The second bug is rather obvious too. No osmosis skinengine. No TinyPlayer. Classic-esque skinengine only. This is because the doublesize algorithm hates you and wants you to go die in a fire.
author nenolod
date Sun, 05 Nov 2006 04:43:16 -0800
parents f6856d226afb
children e090f66574f6
files ChangeLog audacious/dock.c audacious/dock.h audacious/equalizer.c audacious/equalizer.h audacious/main.c audacious/main.h audacious/mainwin.c audacious/ui_playlist.c audacious/util.c audacious/util.h audacious/widgets/skin.c audacious/widgets/skin.h audacious/widgets/svis.c audacious/widgets/vis.c audacious/widgets/vis.h
diffstat 16 files changed, 775 insertions(+), 209 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog	Sun Nov 05 02:38:25 2006 -0800
+++ b/ChangeLog	Sun Nov 05 04:43:16 2006 -0800
@@ -1,3 +1,11 @@
+2006-11-05 10:38:25 +0000  William Pitcock <nenolod@nenolod.net>
+  revision [2831]
+  - update documentation per bug #605
+  
+  trunk/README |    7 -------
+  1 file changed, 7 deletions(-)
+
+
 2006-11-05 10:29:47 +0000  William Pitcock <nenolod@nenolod.net>
   revision [2829]
   - per bug #605, remove GNOME VFS.
--- a/audacious/dock.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/dock.c	Sun Nov 05 04:43:16 2006 -0800
@@ -289,7 +289,7 @@
     return shade_list;
 }
 
-static void
+void
 dock_window_resize(GtkWindow * widget, gint new_w, gint new_h, gint w, gint h)
 {
     gdk_window_set_hints(GTK_WIDGET(widget)->window, 0, 0, MIN(w, new_w),
--- a/audacious/dock.h	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/dock.h	Sun Nov 05 04:43:16 2006 -0800
@@ -38,5 +38,6 @@
 
 GList *dock_window_set_decorated(GList * list, GtkWindow * window,
                                  gboolean decorated);
+void dock_window_resize(GtkWindow * widget, gint new_w, gint new_h, gint w, gint h);
 
 #endif
--- a/audacious/equalizer.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/equalizer.c	Sun Nov 05 04:43:16 2006 -0800
@@ -93,7 +93,7 @@
 static GtkWidget *equalizerwin_delete_window = NULL;
 static GtkWidget *equalizerwin_delete_auto_window = NULL;
 
-static GdkPixmap *equalizerwin_bg;
+static GdkPixmap *equalizerwin_bg, *equalizerwin_bg_x2;
 static GdkGC *equalizerwin_gc;
 
 static GList *equalizerwin_wlist = NULL;
@@ -180,15 +180,41 @@
 static void
 equalizerwin_set_shape_mask(void)
 {
-    GdkBitmap *mask;
-
     if (cfg.show_wm_decorations)
         return;
 
-    mask = skin_get_mask(bmp_active_skin, SKIN_MASK_EQ + cfg.equalizer_shaded);
-    gtk_widget_shape_combine_mask(equalizerwin, mask, 0, 0);
+    if (cfg.doublesize == FALSE)
+        gtk_widget_shape_combine_mask(equalizerwin,
+                                      skin_get_mask(bmp_active_skin,
+                                                    SKIN_MASK_EQ), 0, 0);
+    else
+        gtk_widget_shape_combine_mask(equalizerwin, NULL, 0, 0);
 }
 
+void
+equalizerwin_set_doublesize(gboolean ds)
+{
+    gint height;
+
+    if (cfg.equalizer_shaded)
+        height = 14;
+    else
+        height = 116;
+
+    equalizerwin_set_shape_mask();
+
+    if (ds) {
+        dock_window_resize(equalizerwin, 275, height, 550, height * 2);
+        gdk_window_set_back_pixmap(equalizerwin->window, equalizerwin_bg_x2,
+                                   0);
+    }
+    else {
+        dock_window_resize(equalizerwin, 275, height, 275, height);
+        gdk_window_set_back_pixmap(equalizerwin->window, equalizerwin_bg, 0);
+    }
+
+    draw_equalizer_window(TRUE);
+}
 
 void
 equalizerwin_set_shade_menu_cb(gboolean shaded)
@@ -198,7 +224,8 @@
     equalizerwin_set_shape_mask();
 
     if (shaded) {
-        dock_shade(dock_window_list, GTK_WINDOW(equalizerwin), 14);
+        dock_shade(dock_window_list, GTK_WINDOW(equalizerwin),
+                   14 * (EQUALIZER_DOUBLESIZE + 1));
         pbutton_set_button_data(equalizerwin_shade, -1, 3, -1, 47);
         pbutton_set_skin_index1(equalizerwin_shade, SKIN_EQ_EX);
         pbutton_set_button_data(equalizerwin_close, 11, 38, 11, 47);
@@ -207,7 +234,8 @@
         widget_show(WIDGET(equalizerwin_balance));
     }
     else {
-        dock_shade(dock_window_list, GTK_WINDOW(equalizerwin), 116);
+        dock_shade(dock_window_list, GTK_WINDOW(equalizerwin),
+                   116 * (EQUALIZER_DOUBLESIZE + 1));
         pbutton_set_button_data(equalizerwin_shade, -1, 137, -1, 38);
         pbutton_set_skin_index1(equalizerwin_shade, SKIN_EQMAIN);
         pbutton_set_button_data(equalizerwin_close, 0, 116, 0, 125);
@@ -286,6 +314,9 @@
 void
 draw_equalizer_window(gboolean force)
 {
+    GdkImage *img, *img2;
+    GList *wl;
+    Widget *w;
     gboolean redraw;
 
     widget_list_lock(equalizerwin_wlist);
@@ -320,7 +351,36 @@
     widget_list_draw(equalizerwin_wlist, &redraw, force);
 
     if (force || redraw) {
-        widget_list_clear_redraw(equalizerwin_wlist);
+        if (cfg.doublesize && cfg.eq_doublesize_linked) {
+            if (force) {
+                img = gdk_drawable_get_image(equalizerwin_bg, 0, 0, 275, 116);
+                img2 = create_dblsize_image(img);
+                gdk_draw_image(equalizerwin_bg_x2, equalizerwin_gc,
+                               img2, 0, 0, 0, 0, 550, 232);
+                gdk_image_destroy(img2);
+                gdk_image_destroy(img);
+            }
+            else {
+                for (wl = equalizerwin_wlist; wl; wl = g_list_next(wl)) {
+                    w = WIDGET(wl->data);
+                    if (w->redraw && w->visible) {
+                        img = gdk_drawable_get_image(equalizerwin_bg,
+                                                     w->x, w->y,
+                                                     w->width, w->height);
+                        img2 = create_dblsize_image(img);
+                        gdk_draw_image(equalizerwin_bg_x2,
+                                       equalizerwin_gc, img2, 0, 0,
+                                       w->x << 1, w->y << 1, w->width << 1,
+                                       w->height << 1);
+                        gdk_image_destroy(img2);
+                        gdk_image_destroy(img);
+                        w->redraw = FALSE;
+                    }
+                }
+            }
+        }
+        else
+            widget_list_clear_redraw(equalizerwin_wlist);
         gdk_window_clear(equalizerwin->window);
         gdk_flush();
     }
@@ -360,9 +420,13 @@
 
     mx = event->x;
     my = event->y;
+    if (cfg.doublesize && cfg.eq_doublesize_linked) {
+        event->x /= 2;
+        event->y /= 2;
+    }
 
     if (event->button == 1 && event->type == GDK_BUTTON_PRESS &&
-        ((cfg.equalizer_shaded || event->y < 14) &&
+        ((cfg.easy_move || cfg.equalizer_shaded || event->y < 14) &&
          !inside_sensitive_widgets(event->x, event->y))) {
         if (0 && hint_move_resize_available()) {
             hint_move_resize(equalizerwin, event->x_root,
@@ -407,6 +471,11 @@
 static void
 equalizerwin_scroll(GtkWidget * widget, GdkEventScroll * event, gpointer data)
 {
+    if (cfg.doublesize && cfg.eq_doublesize_linked) {
+        event->x /= 2;
+        event->y /= 2;
+    }
+
     handle_scroll_cb(equalizerwin_wlist, widget, event);
     draw_equalizer_window(FALSE);
 }
@@ -441,6 +510,10 @@
     gdk_pointer_ungrab(GDK_CURRENT_TIME);
     gdk_flush();
 
+    if (cfg.doublesize && cfg.eq_doublesize_linked) {
+        event->x /= 2;
+        event->y /= 2;
+    }
     if (dock_is_moving(GTK_WINDOW(equalizerwin))) {
         dock_move_release(GTK_WINDOW(equalizerwin));
     }
@@ -517,7 +590,11 @@
 static void
 equalizerwin_set_back_pixmap(void)
 {
-    gdk_window_set_back_pixmap(equalizerwin->window, equalizerwin_bg, 0);
+    if (cfg.doublesize && cfg.eq_doublesize_linked)
+        gdk_window_set_back_pixmap(equalizerwin->window, equalizerwin_bg_x2,
+                                   0);
+    else
+        gdk_window_set_back_pixmap(equalizerwin->window, equalizerwin_bg, 0);
     gdk_window_clear(equalizerwin->window);
 }
 
@@ -743,6 +820,11 @@
     width = 275;
     height = cfg.equalizer_shaded ? 14 : 116;
 
+    if (cfg.doublesize && cfg.eq_doublesize_linked) {
+        width *= 2;
+        height *= 2;
+    }
+
     gtk_window_set_default_size(GTK_WINDOW(equalizerwin), width, height);
     gtk_window_set_resizable(GTK_WINDOW(equalizerwin), FALSE);
 
@@ -817,11 +899,16 @@
 
     equalizerwin_gc = gdk_gc_new(equalizerwin->window);
     equalizerwin_bg = gdk_pixmap_new(equalizerwin->window, 275, 116, -1);
+    equalizerwin_bg_x2 = gdk_pixmap_new(equalizerwin->window, 550, 232, -1);
 
     equalizerwin_create_widgets();
 
     equalizerwin_set_back_pixmap();
-    gdk_window_set_back_pixmap(equalizerwin->window, equalizerwin_bg, 0);
+    if (cfg.doublesize && cfg.eq_doublesize_linked)
+        gdk_window_set_back_pixmap(equalizerwin->window,
+                                   equalizerwin_bg_x2, 0);
+    else
+        gdk_window_set_back_pixmap(equalizerwin->window, equalizerwin_bg, 0);
 }
 
 
@@ -845,8 +932,12 @@
 
     gtk_window_get_position(GTK_WINDOW(equalizerwin), &x, &y);
     gtk_window_move(GTK_WINDOW(equalizerwin), x, y);
-    gtk_widget_set_size_request(equalizerwin, 275,
-                                (cfg.equalizer_shaded ? 14 : 116));
+    if (cfg.doublesize && cfg.eq_doublesize_linked)
+        gtk_widget_set_size_request(equalizerwin, 550,
+                                    (cfg.equalizer_shaded ? 28 : 232));
+    else
+        gtk_widget_set_size_request(equalizerwin, 275,
+                                    (cfg.equalizer_shaded ? 14 : 116));
     gdk_flush();
     draw_equalizer_window(TRUE);
     cfg.equalizer_visible = TRUE;
--- a/audacious/equalizer.h	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/equalizer.h	Sun Nov 05 04:43:16 2006 -0800
@@ -1,4 +1,7 @@
-/*  BMP - Cross-platform multimedia player
+/*  Audacious
+ *  Copyright (C) 2005-2006  Audacious development team.
+ *
+ *  BMP - Cross-platform multimedia player
  *  Copyright (C) 2003-2004  BMP development team.
  *
  *  Based on XMMS:
@@ -27,8 +30,9 @@
 
 #include "widgets/widgetcore.h"
 
-#define EQUALIZER_HEIGHT         (gint)(cfg.equalizer_shaded ? 14 : 116)
-#define EQUALIZER_WIDTH          (gint)275
+#define EQUALIZER_DOUBLESIZE     (cfg.doublesize && cfg.eq_doublesize_linked)
+#define EQUALIZER_HEIGHT         ((cfg.equalizer_shaded ? 14 : 116) * (EQUALIZER_DOUBLESIZE + 1))
+#define EQUALIZER_WIDTH          (275 * (EQUALIZER_DOUBLESIZE + 1))
 
 #define EQUALIZER_DEFAULT_POS_X  20
 #define EQUALIZER_DEFAULT_POS_Y  136
@@ -36,6 +40,7 @@
 #define EQUALIZER_DEFAULT_DIR_PRESET "dir_default.preset"
 #define EQUALIZER_DEFAULT_PRESET_EXT "preset"
 
+void equalizerwin_set_doublesize(gboolean ds);
 void equalizerwin_set_shade_menu_cb(gboolean shaded);
 void draw_equalizer_window(gboolean force);
 void equalizerwin_create(void);
--- a/audacious/main.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/main.c	Sun Nov 05 04:43:16 2006 -0800
@@ -264,6 +264,7 @@
     {"dim_titlebar", &cfg.dim_titlebar, TRUE},
     {"get_info_on_load", &cfg.get_info_on_load, TRUE},
     {"get_info_on_demand", &cfg.get_info_on_demand, TRUE},
+    {"eq_doublesize_linked", &cfg.eq_doublesize_linked, TRUE},
     {"no_playlist_advance", &cfg.no_playlist_advance, TRUE},
     {"refresh_file_list", &cfg.refresh_file_list, TRUE},
     {"sort_jump_to_file", &cfg.sort_jump_to_file, TRUE},
@@ -274,6 +275,7 @@
     {"player_visible", &cfg.player_visible, TRUE},
     {"shuffle", &cfg.shuffle, TRUE},
     {"repeat", &cfg.repeat, TRUE},
+    {"doublesize", &cfg.doublesize, TRUE},
     {"autoscroll_songname", &cfg.autoscroll, TRUE},
     {"stop_after_current_song", &cfg.stopaftersong, TRUE},
     {"playlist_shaded", &cfg.playlist_shaded, TRUE},
@@ -285,6 +287,7 @@
     {"equalizer_active", &cfg.equalizer_active, TRUE},
     {"equalizer_shaded", &cfg.equalizer_shaded, TRUE},
     {"equalizer_autoload", &cfg.equalizer_autoload, TRUE},
+    {"easy_move", &cfg.easy_move, TRUE},
     {"use_eplugins", &cfg.use_eplugins, TRUE},
     {"always_on_top", &cfg.always_on_top, TRUE},
     {"sticky", &cfg.sticky, TRUE},
--- a/audacious/main.h	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/main.h	Sun Nov 05 04:43:16 2006 -0800
@@ -45,8 +45,9 @@
 #define BMP_LOG_BASENAME              "log"
 
 #define PLAYER_HEIGHT \
-  (cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : MAINWIN_HEIGHT)
-#define PLAYER_WIDTH  MAINWIN_WIDTH
+  ((cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : MAINWIN_HEIGHT) * (cfg.doublesize + 1))
+#define PLAYER_WIDTH \
+  (MAINWIN_WIDTH * (cfg.doublesize + 1))
 
 struct _BmpConfig {
     gint player_x, player_y;
--- a/audacious/mainwin.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/mainwin.c	Sun Nov 05 04:43:16 2006 -0800
@@ -119,7 +119,7 @@
     MAINWIN_OPT_STICKY,
     MAINWIN_OPT_WS,
     MAINWIN_OPT_PWS,
-    MAINWIN_OPT_EQWS
+    MAINWIN_OPT_EQWS, MAINWIN_OPT_DOUBLESIZE, MAINWIN_OPT_EASY_MOVE
 };
 
 enum {
@@ -173,7 +173,7 @@
 gint seek_initial_pos = 0;
 
 GdkGC *mainwin_gc;
-static GdkPixmap *mainwin_bg = NULL;
+static GdkPixmap *mainwin_bg = NULL, *mainwin_bg_x2 = NULL;
 
 GtkAccelGroup *mainwin_accel = NULL;
 
@@ -438,7 +438,12 @@
     {N_("/Roll up Playlist Editor"), "<control><shift>W", mainwin_view_menu_callback,
      MAINWIN_OPT_PWS, "<ToggleItem>", NULL},
     {N_("/Roll up Equalizer"), "<control><alt>W", mainwin_view_menu_callback,
-     MAINWIN_OPT_EQWS, "<ToggleItem>", NULL}
+     MAINWIN_OPT_EQWS, "<ToggleItem>", NULL},
+    {"/-", NULL, NULL, 0, "<Separator>", NULL},
+    {N_("/DoubleSize"), "<control>D", mainwin_view_menu_callback,
+     MAINWIN_OPT_DOUBLESIZE, "<ToggleItem>"},
+    {N_("/Easy Move"), "<control>E", mainwin_view_menu_callback,
+     MAINWIN_OPT_EASY_MOVE, "<ToggleItem>"}
 };
 
 static const gint mainwin_view_menu_entries_num =
@@ -458,6 +463,8 @@
 void mainwin_position_motion_cb(gint pos);
 void mainwin_position_release_cb(gint pos);
 
+void set_doublesize(gboolean doublesize);
+
 
 /* FIXME: placed here for now */
 void
@@ -510,13 +517,15 @@
 static void
 mainwin_set_shape_mask(void)
 {
-    GdkBitmap *mask;
-
     if (!cfg.player_visible)
         return;
 
-    mask = skin_get_mask(bmp_active_skin, SKIN_MASK_MAIN + cfg.player_shaded);
-    gtk_widget_shape_combine_mask(mainwin, mask, 0, 0);
+    if (cfg.doublesize == FALSE)
+        gtk_widget_shape_combine_mask(mainwin,
+                                  skin_get_mask(bmp_active_skin,
+                                                SKIN_MASK_MAIN), 0, 0);
+    else
+        gtk_widget_shape_combine_mask(mainwin, NULL, 0, 0);
 }
 
 static void
@@ -537,7 +546,7 @@
 
     if (shaded) {
         dock_shade(dock_window_list, GTK_WINDOW(mainwin),
-                   MAINWIN_SHADED_HEIGHT);
+                   MAINWIN_SHADED_HEIGHT * (cfg.doublesize + 1));
 
         widget_show(WIDGET(mainwin_svis));
         vis_clear_data(mainwin_vis);
@@ -566,9 +575,10 @@
         mainwin_shade->pb_ny = mainwin_shade->pb_py = 27;
     }
     else {
-        dock_shade(dock_window_list, GTK_WINDOW(mainwin),
-		!bmp_active_skin->properties.mainwin_height ? MAINWIN_HEIGHT :
-		     bmp_active_skin->properties.mainwin_height);
+	gint height = !bmp_active_skin->properties.mainwin_height ? MAINWIN_HEIGHT :
+                     bmp_active_skin->properties.mainwin_height;
+
+        dock_shade(dock_window_list, GTK_WINDOW(mainwin), height * (cfg.doublesize + 1));
 
         widget_hide(WIDGET(mainwin_svis));
         svis_clear_data(mainwin_svis);
@@ -659,8 +669,8 @@
     gint x, y;
     gtk_window_get_position(GTK_WINDOW(mainwin), &x, &y);
     util_item_factory_popup(mainwin_general_menu,
-                            x + 6,
-                            y + MAINWIN_SHADED_HEIGHT,
+                            x + 6 * (1 + cfg.doublesize),
+                            y + MAINWIN_SHADED_HEIGHT * (1 + cfg.doublesize),
                             1, GDK_CURRENT_TIME);
 }
 
@@ -722,6 +732,7 @@
 void
 draw_main_window(gboolean force)
 {
+    GdkImage *img, *img2x;
     GList *wl;
     Widget *w;
     gboolean redraw;
@@ -747,7 +758,22 @@
 
     if (redraw || force) {
         if (force) {
+            if (cfg.doublesize) {
+                img = gdk_drawable_get_image(mainwin_bg, 0, 0, bmp_active_skin->properties.mainwin_width,
+                                             cfg.player_shaded ?
+                                             MAINWIN_SHADED_HEIGHT :
+                                             bmp_active_skin->properties.mainwin_height);
+                img2x = create_dblsize_image(img);
+                gdk_draw_image(mainwin_bg_x2, mainwin_gc, img2x, 0, 0,
+                               0, 0, MAINWIN_WIDTH * 2,
+                               cfg.player_shaded ? MAINWIN_SHADED_HEIGHT *
+                               2 : MAINWIN_HEIGHT * 2);
+                gdk_image_destroy(img2x);
+                gdk_image_destroy(img);
+            }
+
             gdk_window_clear(mainwin->window);
+
         }
         else {
             for (wl = mainwin_wlist; wl; wl = g_list_next(wl)) {
@@ -756,8 +782,22 @@
                 if (!w->redraw || !w->visible)
                     continue;
 
-                gdk_window_clear_area(mainwin->window, w->x, w->y,
-                                      w->width, w->height);
+                if (cfg.doublesize) {
+                    img = gdk_drawable_get_image(mainwin_bg, w->x, w->y,
+                                                 w->width, w->height);
+                    img2x = create_dblsize_image(img);
+                    gdk_draw_image(mainwin_bg_x2, mainwin_gc,
+                                   img2x, 0, 0, w->x << 1, w->y << 1,
+                                   w->width << 1, w->height << 1);
+                    gdk_image_destroy(img2x);
+                    gdk_image_destroy(img);
+                    gdk_window_clear_area(mainwin->window, w->x << 1,
+                                          w->y << 1, w->width << 1,
+                                          w->height << 1);
+                }
+                else
+                    gdk_window_clear_area(mainwin->window, w->x, w->y,
+                                          w->width, w->height);
                 w->redraw = FALSE;
             }
         }
@@ -998,30 +1038,25 @@
 
 	gdk_window_get_size(mainwin->window, &width, &height);
 
-	if (width == bmp_active_skin->properties.mainwin_width &&
-		height == bmp_active_skin->properties.mainwin_height)
+	if (width == bmp_active_skin->properties.mainwin_width * (cfg.doublesize + 1) &&
+		height == bmp_active_skin->properties.mainwin_height * (cfg.doublesize + 1))
 	{
 		return;
 	}
 
-        gdk_window_set_hints(mainwin->window, 0, 0,
-                                cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width,
-                                cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height,
-                                cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width,
-                                cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height,
-                                GDK_HINT_MIN_SIZE | GDK_HINT_MAX_SIZE);
-        gdk_window_resize(mainwin->window, cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width,
-		cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height);
-        gdk_window_set_hints(mainwin->window, 0, 0,
-                                cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width,
-                                cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height,
-                                cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width,
-                                cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height,
-                                GDK_HINT_MIN_SIZE | GDK_HINT_MAX_SIZE);
+        dock_window_resize(GTK_WINDOW(mainwin), cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width,
+		cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height,
+		bmp_active_skin->properties.mainwin_width * (cfg.doublesize + 1),
+		bmp_active_skin->properties.mainwin_height * (cfg.doublesize + 1));
+
 	g_object_unref(mainwin_bg);
+	g_object_unref(mainwin_bg_x2);
         mainwin_bg = gdk_pixmap_new(mainwin->window,
 				bmp_active_skin->properties.mainwin_width,
 				bmp_active_skin->properties.mainwin_height, -1);
+        mainwin_bg_x2 = gdk_pixmap_new(mainwin->window,
+				bmp_active_skin->properties.mainwin_width * 2,
+				bmp_active_skin->properties.mainwin_height * 2, -1);
         mainwin_set_back_pixmap();
 	widget_list_change_pixmap(mainwin_wlist, mainwin_bg);
 	gdk_flush();
@@ -1243,7 +1278,10 @@
         y = event->y;
         state = event->state;
     }
-
+    if (cfg.doublesize) {
+        event->x /= 2;
+        event->y /= 2;
+    }
     if (dock_is_moving(GTK_WINDOW(mainwin))) {
         dock_move_motion(GTK_WINDOW(mainwin), event);
     }
@@ -1335,8 +1373,19 @@
 
     gboolean grab = TRUE;
 
+    if (cfg.doublesize) {
+        /*
+         * A hack to make doublesize transparent to callbacks.
+         * We should make a copy of this data instead of
+         * tampering with the data we get from gtk+
+         */
+        event->x /= 2;
+        event->y /= 2;
+    }
+
     if (event->button == 1 && event->type == GDK_BUTTON_PRESS &&
-        !inside_sensitive_widgets(event->x, event->y) && event->y < 14) {
+        !inside_sensitive_widgets(event->x, event->y) &&
+        (cfg.easy_move || event->y < 14)) {
         if (0 && hint_move_resize_available()) {
             hint_move_resize(mainwin, event->x_root, event->y_root, TRUE);
             grab = FALSE;
@@ -2133,7 +2182,10 @@
 void
 mainwin_set_back_pixmap(void)
 {
-    gdk_window_set_back_pixmap(mainwin->window, mainwin_bg, 0);
+    if (cfg.doublesize)
+        gdk_window_set_back_pixmap(mainwin->window, mainwin_bg_x2, 0);
+    else
+        gdk_window_set_back_pixmap(mainwin->window, mainwin_bg, 0);
     gdk_window_clear(mainwin->window);
 }
 
@@ -2738,6 +2790,44 @@
     }
 }
 
+static void
+mainwin_set_doublesize(gboolean doublesize)
+{
+    gint height;
+
+    if (cfg.player_shaded)
+        height = MAINWIN_SHADED_HEIGHT;
+    else
+        height = bmp_active_skin->properties.mainwin_height;
+
+    mainwin_set_shape_mask();
+
+    dock_window_resize(GTK_WINDOW(mainwin), cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width,
+		cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height,
+		bmp_active_skin->properties.mainwin_width * 2, bmp_active_skin->properties.mainwin_height * 2);
+
+    if (cfg.doublesize) {
+        gdk_window_set_back_pixmap(mainwin->window, mainwin_bg_x2, 0);
+    }
+    else {
+        gdk_window_set_back_pixmap(mainwin->window, mainwin_bg, 0);
+    }
+
+    draw_main_window(TRUE);
+    vis_set_doublesize(mainwin_vis, doublesize);
+}
+
+void
+set_doublesize(gboolean doublesize)
+{
+    cfg.doublesize = doublesize;
+
+    mainwin_set_doublesize(doublesize);
+
+    if (cfg.eq_doublesize_linked)
+        equalizerwin_set_doublesize(doublesize);
+}
+
                                
 static void
 mainwin_view_menu_callback(gpointer data,
@@ -2775,6 +2865,20 @@
     case MAINWIN_OPT_EQWS:
         equalizerwin_set_shade_menu_cb(GTK_CHECK_MENU_ITEM(item)->active);
         break;
+    case MAINWIN_OPT_DOUBLESIZE:
+        mainwin_menurow->mr_doublesize_selected =
+            GTK_CHECK_MENU_ITEM(gtk_item_factory_get_widget
+                                (mainwin_view_menu,
+                                 "/DoubleSize"))->active;
+        widget_draw(WIDGET(mainwin_menurow));
+        set_doublesize(mainwin_menurow->mr_doublesize_selected);
+        gdk_flush();
+        break;
+    case MAINWIN_OPT_EASY_MOVE:
+        cfg.easy_move =
+            GTK_CHECK_MENU_ITEM(gtk_item_factory_get_widget
+                                (mainwin_view_menu, "/Easy Move"))->active;
+        break;
     case MAINWIN_SONGNAME_SCROLL:
         check = GTK_CHECK_MENU_ITEM(item);
         mainwin_set_title_scroll(gtk_check_menu_item_get_active(check));
@@ -2968,7 +3072,10 @@
         mainwin_lock_info_text(_("FILE INFO BOX"));
         break;
     case MENUROW_DOUBLESIZE:
-        mainwin_lock_info_text(_("** DOUBLESIZE HAS BEEN REMOVED **"));
+        if (mainwin_menurow->mr_doublesize_selected)
+            mainwin_lock_info_text(_("DISABLE DOUBLESIZE"));
+        else
+            mainwin_lock_info_text(_("ENABLE DOUBLESIZE"));
         break;
     case MENUROW_VISUALIZATION:
         mainwin_lock_info_text(_("VISUALIZATION MENU"));
@@ -3000,7 +3107,10 @@
         playlist_fileinfo_current();
         break;
     case MENUROW_DOUBLESIZE:
-        /* double size removed, do nothing */
+        widget =
+            gtk_item_factory_get_widget(mainwin_view_menu, "/DoubleSize");
+        gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(widget),
+                                       mainwin_menurow->mr_doublesize_selected);
         break;
     case MENUROW_VISUALIZATION:
         gdk_window_get_pointer(NULL, &x, &y, &modmask);
@@ -3268,6 +3378,8 @@
     check_set(mainwin_view_menu, "/Roll up Player", cfg.player_shaded);
     check_set(mainwin_view_menu, "/Roll up Playlist Editor", cfg.playlist_shaded);
     check_set(mainwin_view_menu, "/Roll up Equalizer", cfg.equalizer_shaded);
+    check_set(mainwin_view_menu, "/Easy Move", cfg.easy_move);
+    check_set(mainwin_view_menu, "/DoubleSize", cfg.doublesize);
 
     /* Songname menu */
 
@@ -3422,7 +3534,7 @@
         create_menurow(&mainwin_wlist, mainwin_bg, mainwin_gc, 10, 22, 304,
                        0, 304, 44, mainwin_mr_change, mainwin_mr_release,
                        SKIN_TITLEBAR);
-    mainwin_menurow->mr_doublesize_selected = FALSE;
+    mainwin_menurow->mr_doublesize_selected = cfg.doublesize;
     mainwin_menurow->mr_always_selected = cfg.always_on_top;
 
     mainwin_volume =
@@ -3473,7 +3585,7 @@
 
     mainwin_vis =
         create_vis(&mainwin_wlist, mainwin_bg, mainwin->window, mainwin_gc,
-                   24, 43, 76);
+                   24, 43, 76, cfg.doublesize);
     mainwin_svis = create_svis(&mainwin_wlist, mainwin_bg, mainwin_gc, 79, 5);
     active_vis = mainwin_vis;
 
@@ -3534,6 +3646,11 @@
     width = cfg.player_shaded ? MAINWIN_SHADED_WIDTH : bmp_active_skin->properties.mainwin_width;
     height = cfg.player_shaded ? MAINWIN_SHADED_HEIGHT : bmp_active_skin->properties.mainwin_height;
 
+    if (cfg.doublesize) {
+        width *= 2;
+        height *= 2;
+    }
+
     gtk_widget_set_size_request(mainwin, width, height);
     gtk_widget_set_app_paintable(mainwin, TRUE);
 
@@ -3623,6 +3740,9 @@
     mainwin_bg = gdk_pixmap_new(mainwin->window,
                                 bmp_active_skin->properties.mainwin_width,
 				bmp_active_skin->properties.mainwin_height, -1);
+    mainwin_bg_x2 = gdk_pixmap_new(mainwin->window,
+                                bmp_active_skin->properties.mainwin_width * 2,
+				bmp_active_skin->properties.mainwin_height * 2, -1);
     mainwin_set_back_pixmap();
     mainwin_create_widgets();
 
--- a/audacious/ui_playlist.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/ui_playlist.c	Sun Nov 05 04:43:16 2006 -0800
@@ -1205,7 +1205,7 @@
                               GDK_TARGET_STRING, event->time);
     }
     else if (event->button == 1 && event->type == GDK_BUTTON_PRESS &&
-             !inside_sensitive_widgets(event->x, event->y) && event->y < 14)
+             !inside_sensitive_widgets(event->x, event->y) && (cfg.easy_move || event->y < 14))
     {
         dock_move_press(dock_window_list, GTK_WINDOW(playlistwin), event,
                         FALSE);
--- a/audacious/util.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/util.c	Sun Nov 05 04:43:16 2006 -0800
@@ -1817,3 +1817,109 @@
 
 	return out;
 }
+
+GdkImage *create_dblsize_image(GdkImage * img)
+{
+    GdkImage *dblimg;
+    register guint x, y;
+
+    /*
+     * This needs to be optimized
+     */
+
+    dblimg =
+	gdk_image_new(GDK_IMAGE_NORMAL, gdk_visual_get_best(),
+		      img->width << 1, img->height << 1);
+    if (dblimg->bpp == 1) {
+	register guint8 *srcptr, *ptr, *ptr2, pix;
+
+	srcptr = GDK_IMAGE_XIMAGE(img)->data;
+	ptr = GDK_IMAGE_XIMAGE(dblimg)->data;
+	ptr2 = ptr + dblimg->bpl;
+
+	for (y = 0; y < img->height; y++) {
+	    for (x = 0; x < img->width; x++) {
+		pix = *srcptr++;
+		*ptr++ = pix;
+		*ptr++ = pix;
+		*ptr2++ = pix;
+		*ptr2++ = pix;
+	    }
+	    srcptr += img->bpl - img->width;
+	    ptr += (dblimg->bpl << 1) - dblimg->width;
+	    ptr2 += (dblimg->bpl << 1) - dblimg->width;
+	}
+    }
+    if (dblimg->bpp == 2) {
+	guint16 *srcptr, *ptr, *ptr2, pix;
+
+	srcptr = (guint16 *) GDK_IMAGE_XIMAGE(img)->data;
+	ptr = (guint16 *) GDK_IMAGE_XIMAGE(dblimg)->data;
+	ptr2 = ptr + (dblimg->bpl >> 1);
+
+	for (y = 0; y < img->height; y++) {
+	    for (x = 0; x < img->width; x++) {
+		pix = *srcptr++;
+		*ptr++ = pix;
+		*ptr++ = pix;
+		*ptr2++ = pix;
+		*ptr2++ = pix;
+	    }
+	    srcptr += (img->bpl >> 1) - img->width;
+	    ptr += (dblimg->bpl) - dblimg->width;
+	    ptr2 += (dblimg->bpl) - dblimg->width;
+	}
+    }
+    if (dblimg->bpp == 3) {
+	register guint8 *srcptr, *ptr, *ptr2, pix1, pix2, pix3;
+
+	srcptr = GDK_IMAGE_XIMAGE(img)->data;
+	ptr = GDK_IMAGE_XIMAGE(dblimg)->data;
+	ptr2 = ptr + dblimg->bpl;
+
+	for (y = 0; y < img->height; y++) {
+	    for (x = 0; x < img->width; x++) {
+		pix1 = *srcptr++;
+		pix2 = *srcptr++;
+		pix3 = *srcptr++;
+		*ptr++ = pix1;
+		*ptr++ = pix2;
+		*ptr++ = pix3;
+		*ptr++ = pix1;
+		*ptr++ = pix2;
+		*ptr++ = pix3;
+		*ptr2++ = pix1;
+		*ptr2++ = pix2;
+		*ptr2++ = pix3;
+		*ptr2++ = pix1;
+		*ptr2++ = pix2;
+		*ptr2++ = pix3;
+
+	    }
+	    srcptr += img->bpl - (img->width * 3);
+	    ptr += (dblimg->bpl << 1) - (dblimg->width * 3);
+	    ptr2 += (dblimg->bpl << 1) - (dblimg->width * 3);
+	}
+    }
+    if (dblimg->bpp == 4) {
+	register guint32 *srcptr, *ptr, *ptr2, pix;
+
+	srcptr = (guint32 *) GDK_IMAGE_XIMAGE(img)->data;
+	ptr = (guint32 *) GDK_IMAGE_XIMAGE(dblimg)->data;
+	ptr2 = ptr + (dblimg->bpl >> 2);
+
+	for (y = 0; y < img->height; y++) {
+	    for (x = 0; x < img->width; x++) {
+		pix = *srcptr++;
+		*ptr++ = pix;
+		*ptr++ = pix;
+		*ptr2++ = pix;
+		*ptr2++ = pix;
+	    }
+	    srcptr += (img->bpl >> 2) - img->width;
+	    ptr += (dblimg->bpl >> 1) - dblimg->width;
+	    ptr2 += (dblimg->bpl >> 1) - dblimg->width;
+	}
+    }
+    return dblimg;
+}
--- a/audacious/util.h	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/util.h	Sun Nov 05 04:43:16 2006 -0800
@@ -146,6 +146,8 @@
 gboolean xmms_check_realtime_priority(void);
 void xmms_usleep(gint usec);
 
+GdkImage *create_dblsize_image(GdkImage * img);
+
 G_END_DECLS
 
 #endif
--- a/audacious/widgets/skin.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/widgets/skin.c	Sun Nov 05 04:43:16 2006 -0800
@@ -122,19 +122,15 @@
     {200, 200, 200}
 };
 
-static GdkBitmap *
-skin_create_transparent_mask(const gchar *,
-                             const gchar *,
-                             const gchar *,
-                             GdkWindow *,
-                             gint, gint);
+static GdkBitmap *skin_create_transparent_mask(const gchar *,
+                                               const gchar *,
+                                               const gchar *,
+                                               GdkWindow *,
+                                               gint, gint, gboolean);
 
-static void
-skin_setup_masks(Skin * skin);
+static void skin_setup_masks(Skin * skin);
 
-static void
-skin_set_default_vis_color(Skin * skin);
-
+static void skin_set_default_vis_color(Skin * skin);
 
 void
 skin_lock(Skin * skin)
@@ -219,8 +215,11 @@
     for (i = 0; i < SKIN_PIXMAP_COUNT; i++) {
         if (skin->masks[i])
             g_object_unref(skin->masks[i]);
+        if (skin->ds_masks[i])
+            g_object_unref(skin->ds_masks[i]);
 
         skin->masks[i] = NULL;
+        skin->ds_masks[i] = NULL;
     }
 
     skin_set_default_vis_color(skin);
@@ -399,7 +398,13 @@
         skin_create_transparent_mask(path, "region.txt",
                                      skin_mask_info[id].inistr, window,
                                      skin_mask_info[id].width,
-                                     skin_mask_info[id].height);
+                                     skin_mask_info[id].height, FALSE);
+
+    skin->ds_masks[id] =
+        skin_create_transparent_mask(path, "region.txt",
+                                     skin_mask_info[id].inistr, window,
+                                     skin_mask_info[id].width * 2,
+                                     skin_mask_info[id].height * 2, TRUE);
 }
 
 static void
@@ -1203,7 +1208,7 @@
                              const gchar * section,
                              GdkWindow * window,
                              gint width,
-                             gint height)
+                             gint height, gboolean doublesize)
 {
     GdkBitmap *mask = NULL;
     GdkGC *gc = NULL;
@@ -1250,8 +1255,11 @@
             created_mask = TRUE;
             gpoints = g_new(GdkPoint, g_array_index(num, gint, i));
             for (k = 0; k < g_array_index(num, gint, i); k++) {
-                gpoints[k].x = g_array_index(point, gint, j + k * 2);
-                gpoints[k].y = g_array_index(point, gint, j + k * 2 + 1);
+                gpoints[k].x =
+                    g_array_index(point, gint, j + k * 2) * (1 + doublesize);
+                gpoints[k].y =
+                    g_array_index(point, gint,
+                                  j + k * 2 + 1) * (1 + doublesize);
             }
             j += k * 2;
             gdk_draw_polygon(mask, gc, TRUE, gpoints,
@@ -1521,10 +1529,13 @@
 GdkBitmap *
 skin_get_mask(Skin * skin, SkinMaskId mi)
 {
+    GdkBitmap **masks;
+
     g_return_val_if_fail(skin != NULL, NULL);
     g_return_val_if_fail(mi < SKIN_PIXMAP_COUNT, NULL);
 
-    return skin->masks[mi];
+    masks = cfg.doublesize ? skin->ds_masks : skin->masks;
+    return masks[mi];
 }
 
 GdkColor *
--- a/audacious/widgets/skin.h	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/widgets/skin.h	Sun Nov 05 04:43:16 2006 -0800
@@ -196,6 +196,7 @@
     GdkColor *colors[SKIN_COLOR_COUNT];
     guchar vis_color[24][3];
     GdkBitmap *masks[SKIN_MASK_COUNT];
+    GdkBitmap *ds_masks[SKIN_MASK_COUNT];
     SkinProperties properties;
 } Skin;
 
--- a/audacious/widgets/svis.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/widgets/svis.c	Sun Nov 05 04:43:16 2006 -0800
@@ -117,51 +117,103 @@
     }
     cmap = gdk_rgb_cmap_new(colors, 24);
 
-    memset(rgb_data, 0, SVIS_WIDTH * SVIS_HEIGHT);
-    if (cfg.vis_type == VIS_ANALYZER) {
-        switch (cfg.vu_mode) {
-        case VU_NORMAL:
-            for (y = 0; y < 2; y++) {
-                ptr = rgb_data + ((y * 3) * 38);
-                h = (svis->vs_data[y] * 7) / 37;
-                for (x = 0; x < h; x++, ptr += 5) {
-                    c = svis_vu_normal_colors[x];
-                    *(ptr) = c;
-                    *(ptr + 1) = c;
-                    *(ptr + 2) = c;
-                    *(ptr + 38) = c;
-                    *(ptr + 39) = c;
-                    *(ptr + 40) = c;
+    if (!cfg.doublesize) {
+        memset(rgb_data, 0, SVIS_WIDTH * SVIS_HEIGHT);
+        if (cfg.vis_type == VIS_ANALYZER) {
+            switch (cfg.vu_mode) {
+            case VU_NORMAL:
+                for (y = 0; y < 2; y++) {
+                    ptr = rgb_data + ((y * 3) * 38);
+                    h = (svis->vs_data[y] * 7) / 37;
+                    for (x = 0; x < h; x++, ptr += 5) {
+                        c = svis_vu_normal_colors[x];
+                        *(ptr) = c;
+                        *(ptr + 1) = c;
+                        *(ptr + 2) = c;
+                        *(ptr + 38) = c;
+                        *(ptr + 39) = c;
+                        *(ptr + 40) = c;
+                    }
                 }
+                break;
+            case VU_SMOOTH:
+                for (y = 0; y < 2; y++) {
+                    ptr = rgb_data + ((y * 3) * SVIS_WIDTH);
+                    for (x = 0; x < svis->vs_data[y]; x++, ptr++) {
+                        c = 17 - ((x * 15) / 37);
+                        *(ptr) = c;
+                        *(ptr + 38) = c;
+                    }
+                }
+                break;
+            }
+        }
+        else if (cfg.vis_type == VIS_SCOPE) {
+            for (x = 0; x < 38; x++) {
+                h = svis->vs_data[x << 1] / 3;
+                ptr = rgb_data + ((4 - h) * 38) + x;
+                *ptr = svis_scope_colors[h];
             }
-            break;
-        case VU_SMOOTH:
-            for (y = 0; y < 2; y++) {
-                ptr = rgb_data + ((y * 3) * SVIS_WIDTH);
-                for (x = 0; x < svis->vs_data[y]; x++, ptr++) {
-                    c = 17 - ((x * 15) / 37);
-                    *(ptr) = c;
-                    *(ptr + 38) = c;
-                }
-            }
-            break;
         }
+
+        gdk_draw_indexed_image(mainwin->window, mainwin_gc,
+                               svis->vs_widget.x, svis->vs_widget.y,
+                               svis->vs_widget.width,
+                               svis->vs_widget.height,
+                               GDK_RGB_DITHER_NORMAL, (guchar *) rgb_data,
+                               38, cmap);
     }
-    else if (cfg.vis_type == VIS_SCOPE) {
-        for (x = 0; x < 38; x++) {
-            h = svis->vs_data[x << 1] / 3;
-            ptr = rgb_data + ((4 - h) * 38) + x;
-            *ptr = svis_scope_colors[h];
-        }
-    }
+    else {                      /* doublesize */
 
-    gdk_draw_indexed_image(mainwin->window, mainwin_gc,
-                           svis->vs_widget.x, svis->vs_widget.y,
-                           svis->vs_widget.width,
-                           svis->vs_widget.height,
-                           GDK_RGB_DITHER_NORMAL, (guchar *) rgb_data,
-                           38, cmap);
+        memset(rgb_data, 0, SVIS_WIDTH * 2 * SVIS_HEIGHT * 2);
+        if (cfg.vis_type == VIS_ANALYZER) {
+            switch (cfg.vu_mode) {
+            case VU_NORMAL:
+                for (y = 0; y < 2; y++) {
+                    ptr = rgb_data + ((y * 3) * 152);
+                    h = (svis->vs_data[y] * 8) / 37;
+                    for (x = 0; x < h; x++, ptr += 10) {
+                        c = svis_vu_normal_colors[x];
+                        DRAW_DS_PIXEL(ptr, c);
+                        DRAW_DS_PIXEL(ptr + 2, c);
+                        DRAW_DS_PIXEL(ptr + 4, c);
+                        DRAW_DS_PIXEL(ptr + 152, c);
+                        DRAW_DS_PIXEL(ptr + 154, c);
+                        DRAW_DS_PIXEL(ptr + 156, c);
+                    }
+                }
+                break;
+            case VU_SMOOTH:
+                for (y = 0; y < 2; y++) {
+                    ptr = rgb_data + ((y * 3) * 152);
+                    for (x = 0; x < svis->vs_data[y]; x++, ptr += 2) {
+                        c = 17 - ((x * 15) / 37);
+                        DRAW_DS_PIXEL(ptr, c);
+                        DRAW_DS_PIXEL(ptr + 152, c);
+                    }
+                }
+                break;
+            }
+        }
+        else if (cfg.vis_type == VIS_SCOPE) {
+            for (x = 0; x < 38; x++) {
+                h = svis->vs_data[x << 1] / 3;
+                ptr = rgb_data + ((4 - h) * 152) + (x << 1);
+                *ptr = svis_scope_colors[h];
+                *(ptr + 1) = svis_scope_colors[h];
+                *(ptr + 76) = svis_scope_colors[h];
+                *(ptr + 77) = svis_scope_colors[h];
+            }
+        }
 
+        gdk_draw_indexed_image(mainwin->window, mainwin_gc,
+                               svis->vs_widget.x << 1,
+                               svis->vs_widget.y << 1,
+                               svis->vs_widget.width << 1,
+                               svis->vs_widget.height << 1,
+                               GDK_RGB_DITHER_NONE, (guchar *) rgb_data,
+                               76, cmap);
+    }
     gdk_rgb_cmap_free(cmap);
     GDK_THREADS_LEAVE();
 }
@@ -182,9 +234,15 @@
 void
 svis_clear(SVis * svis)
 {
-    gdk_window_clear_area(mainwin->window, svis->vs_widget.x,
-                          svis->vs_widget.y, svis->vs_widget.width,
-                          svis->vs_widget.height);
+    if (!cfg.doublesize)
+        gdk_window_clear_area(mainwin->window, svis->vs_widget.x,
+                              svis->vs_widget.y, svis->vs_widget.width,
+                              svis->vs_widget.height);
+    else
+        gdk_window_clear_area(mainwin->window, svis->vs_widget.x << 1,
+                              svis->vs_widget.y << 1,
+                              svis->vs_widget.width << 1,
+                              svis->vs_widget.height << 1);
 }
 
 SVis *
--- a/audacious/widgets/vis.c	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/widgets/vis.c	Sun Nov 05 04:43:16 2006 -0800
@@ -131,62 +131,83 @@
     }
     cmap = gdk_rgb_cmap_new(colors, 24);
 
-    memset(rgb_data, 0, 76 * 16);
-    for (y = 1; y < 16; y += 2) {
-        ptr = rgb_data + (y * 76);
-        for (x = 0; x < 76; x += 2, ptr += 2)
-            *ptr = 1;
-    }
-    if (cfg.vis_type == VIS_ANALYZER) {
-        for (x = 0; x < 75; x++) {
-            if (cfg.analyzer_type == ANALYZER_BARS && (x % 4) == 0)
-                h = vis->vs_data[x >> 2];
-            else if (cfg.analyzer_type == ANALYZER_LINES)
-                h = vis->vs_data[x];
-            if (h && (cfg.analyzer_type == ANALYZER_LINES ||
-                      (x % 4) != 3)) {
-                ptr = rgb_data + ((16 - h) * 76) + x;
-                switch (cfg.analyzer_mode) {
-                case ANALYZER_NORMAL:
-                    for (y = 0; y < h; y++, ptr += 76)
-                        *ptr = 18 - h + y;
-                    break;
-                case ANALYZER_FIRE:
-                    for (y = 0; y < h; y++, ptr += 76)
-                        *ptr = y + 2;
-                    break;
-                case ANALYZER_VLINES:
-                    for (y = 0; y < h; y++, ptr += 76)
-                        *ptr = 18 - h;
-                    break;
+    if (!vis->vs_doublesize) {
+        memset(rgb_data, 0, 76 * 16);
+        for (y = 1; y < 16; y += 2) {
+            ptr = rgb_data + (y * 76);
+            for (x = 0; x < 76; x += 2, ptr += 2)
+                *ptr = 1;
+        }
+        if (cfg.vis_type == VIS_ANALYZER) {
+            for (x = 0; x < 75; x++) {
+                if (cfg.analyzer_type == ANALYZER_BARS && (x % 4) == 0)
+                    h = vis->vs_data[x >> 2];
+                else if (cfg.analyzer_type == ANALYZER_LINES)
+                    h = vis->vs_data[x];
+                if (h && (cfg.analyzer_type == ANALYZER_LINES ||
+                          (x % 4) != 3)) {
+                    ptr = rgb_data + ((16 - h) * 76) + x;
+                    switch (cfg.analyzer_mode) {
+                    case ANALYZER_NORMAL:
+                        for (y = 0; y < h; y++, ptr += 76)
+                            *ptr = 18 - h + y;
+                        break;
+                    case ANALYZER_FIRE:
+                        for (y = 0; y < h; y++, ptr += 76)
+                            *ptr = y + 2;
+                        break;
+                    case ANALYZER_VLINES:
+                        for (y = 0; y < h; y++, ptr += 76)
+                            *ptr = 18 - h;
+                        break;
+                    }
+                }
+            }
+            if (cfg.analyzer_peaks) {
+                for (x = 0; x < 75; x++) {
+                    if (cfg.analyzer_type == ANALYZER_BARS && (x % 4) == 0)
+                        h = vis->vs_peak[x >> 2];
+                    else if (cfg.analyzer_type == ANALYZER_LINES)
+                        h = vis->vs_peak[x];
+                    if (h
+                        && (cfg.analyzer_type == ANALYZER_LINES
+                            || (x % 4) != 3))
+                        rgb_data[(16 - h) * 76 + x] = 23;
                 }
             }
         }
-        if (cfg.analyzer_peaks) {
+        else if (cfg.vis_type == VIS_SCOPE) {
             for (x = 0; x < 75; x++) {
-                if (cfg.analyzer_type == ANALYZER_BARS && (x % 4) == 0)
-                    h = vis->vs_peak[x >> 2];
-                else if (cfg.analyzer_type == ANALYZER_LINES)
-                    h = vis->vs_peak[x];
-                if (h
-                    && (cfg.analyzer_type == ANALYZER_LINES
-                        || (x % 4) != 3))
-                    rgb_data[(16 - h) * 76 + x] = 23;
-            }
-        }
-    }
-    else if (cfg.vis_type == VIS_SCOPE) {
-        for (x = 0; x < 75; x++) {
-            switch (cfg.scope_mode) {
-            case SCOPE_DOT:
-                h = vis->vs_data[x];
-                ptr = rgb_data + ((15 - h) * 76) + x;
-                *ptr = vis_scope_colors[h];
-                break;
-            case SCOPE_LINE:
-                if (x != 74) {
+                switch (cfg.scope_mode) {
+                case SCOPE_DOT:
+                    h = vis->vs_data[x];
+                    ptr = rgb_data + ((15 - h) * 76) + x;
+                    *ptr = vis_scope_colors[h];
+                    break;
+                case SCOPE_LINE:
+                    if (x != 74) {
+                        h = 15 - vis->vs_data[x];
+                        h2 = 15 - vis->vs_data[x + 1];
+                        if (h > h2) {
+                            y = h;
+                            h = h2;
+                            h2 = y;
+                        }
+                        ptr = rgb_data + (h * 76) + x;
+                        for (y = h; y <= h2; y++, ptr += 76)
+                            *ptr = vis_scope_colors[y - 3];
+
+                    }
+                    else {
+                        h = 15 - vis->vs_data[x];
+                        ptr = rgb_data + (h * 76) + x;
+                        *ptr = vis_scope_colors[h];
+                    }
+                    break;
+                case SCOPE_SOLID:
                     h = 15 - vis->vs_data[x];
-                    h2 = 15 - vis->vs_data[x + 1];
+                    h2 = 9;
+                    c = vis_scope_colors[(gint) vis->vs_data[x]];
                     if (h > h2) {
                         y = h;
                         h = h2;
@@ -194,52 +215,172 @@
                     }
                     ptr = rgb_data + (h * 76) + x;
                     for (y = h; y <= h2; y++, ptr += 76)
-                        *ptr = vis_scope_colors[y - 3];
+                        *ptr = c;
+                    break;
+                }
+            }
+        }
+
+        /* FIXME: The check "shouldn't" be neccessary? */
+/*	if (GTK_IS_WINDOW(vis->vs_window)) { */
+        GDK_THREADS_ENTER();
+        gdk_draw_indexed_image(vis->vs_window, vis->vs_widget.gc,
+                               vis->vs_widget.x, vis->vs_widget.y,
+                               vis->vs_widget.width, vis->vs_widget.height,
+                               GDK_RGB_DITHER_NORMAL, (guchar *) rgb_data,
+                               76, cmap);
+        GDK_THREADS_LEAVE();
+/*	} else {
+		vis->vs_window = mainwin->window;
+	        GDK_THREADS_ENTER();
+	        gdk_draw_indexed_image(vis->vs_window, vis->vs_widget.gc,
+                               vis->vs_widget.x, vis->vs_widget.y,
+                               vis->vs_widget.width, vis->vs_widget.height,
+                               GDK_RGB_DITHER_NORMAL, (guchar *) rgb_data,
+                               76, cmap);
+	        GDK_THREADS_LEAVE();
+        }
+*/
+    }
+    else {
+        memset(rgb_data, 0, 152 * 32);
+        for (y = 1; y < 16; y += 2) {
+            ptr = rgb_data + (y * 304);
+            for (x = 0; x < 76; x += 2, ptr += 4) {
+                *ptr = 1;
+                *(ptr + 1) = 1;
+                *(ptr + 152) = 1;
+                *(ptr + 153) = 1;
+            }
+        }
+        if (cfg.vis_type == VIS_ANALYZER) {
+            for (x = 0; x < 75; x++) {
+                if (cfg.analyzer_type == ANALYZER_BARS && (x % 4) == 0)
+                    h = vis->vs_data[x >> 2];
+                else if (cfg.analyzer_type == ANALYZER_LINES)
+                    h = vis->vs_data[x];
+                if (h
+                    && (cfg.analyzer_type == ANALYZER_LINES
+                        || (x % 4) != 3)) {
+                    ptr = rgb_data + ((16 - h) * 304) + (x << 1);
+                    switch (cfg.analyzer_mode) {
+                    case ANALYZER_NORMAL:
+                        for (y = 0; y < h; y++, ptr += 304) {
+                            *ptr = 18 - h + y;
+                            *(ptr + 1) = 18 - h + y;
+                            *(ptr + 152) = 18 - h + y;
+                            *(ptr + 153) = 18 - h + y;
+                        }
+                        break;
+                    case ANALYZER_FIRE:
+                        for (y = 0; y < h; y++, ptr += 304) {
+                            *ptr = y + 2;
+                            *(ptr + 1) = y + 2;
+                            *(ptr + 152) = y + 2;
+                            *(ptr + 153) = y + 2;
+                        }
+                        break;
+                    case ANALYZER_VLINES:
+                        for (y = 0; y < h; y++, ptr += 304) {
+                            *ptr = 18 - h;
+                            *(ptr + 1) = 18 - h;
+                            *(ptr + 152) = 18 - h;
+                            *(ptr + 153) = 18 - h;
+                        }
+
+                        break;
+                    }
 
                 }
-                else {
-                    h = 15 - vis->vs_data[x];
-                    ptr = rgb_data + (h * 76) + x;
-                    *ptr = vis_scope_colors[h];
+            }
+            if (cfg.analyzer_peaks) {
+
+                for (x = 0; x < 75; x++) {
+                    if (cfg.analyzer_type == ANALYZER_BARS && (x % 4) == 0)
+                        h = vis->vs_peak[x >> 2];
+                    else if (cfg.analyzer_type == ANALYZER_LINES)
+                        h = vis->vs_peak[x];
+
+                    if (h
+                        && (cfg.analyzer_type == ANALYZER_LINES
+                            || (x % 4) != 3)) {
+                        ptr = rgb_data + (16 - h) * 304 + (x << 1);
+                        *ptr = 23;
+                        *(ptr + 1) = 23;
+                        *(ptr + 152) = 23;
+                        *(ptr + 153) = 23;
+                    }
                 }
-                break;
-            case SCOPE_SOLID:
-                h = 15 - vis->vs_data[x];
-                h2 = 9;
-                c = vis_scope_colors[(gint) vis->vs_data[x]];
-                if (h > h2) {
-                    y = h;
-                    h = h2;
-                    h2 = y;
-                }
-                ptr = rgb_data + (h * 76) + x;
-                for (y = h; y <= h2; y++, ptr += 76)
-                    *ptr = c;
-                break;
             }
         }
-    }
+        else if (cfg.vis_type == VIS_SCOPE) {
+            for (x = 0; x < 75; x++) {
+                switch (cfg.scope_mode) {
+                case SCOPE_DOT:
+                    h = vis->vs_data[x];
+                    ptr = rgb_data + ((15 - h) * 304) + (x << 1);
+                    *ptr = vis_scope_colors[h];
+                    *(ptr + 1) = vis_scope_colors[h];
+                    *(ptr + 152) = vis_scope_colors[h];
+                    *(ptr + 153) = vis_scope_colors[h];
+                    break;
+                case SCOPE_LINE:
+                    if (x != 74) {
+                        h = 15 - vis->vs_data[x];
+                        h2 = 15 - vis->vs_data[x + 1];
+                        if (h > h2) {
+                            y = h;
+                            h = h2;
+                            h2 = y;
+                        }
+                        ptr = rgb_data + (h * 304) + (x << 1);
+                        for (y = h; y <= h2; y++, ptr += 304) {
+                            *ptr = vis_scope_colors[y - 3];
+                            *(ptr + 1) = vis_scope_colors[y - 3];
+                            *(ptr + 152) = vis_scope_colors[y - 3];
+                            *(ptr + 153) = vis_scope_colors[y - 3];
+                        }
+                    }
+                    else {
+                        h = 15 - vis->vs_data[x];
+                        ptr = rgb_data + (h * 304) + (x << 1);
+                        *ptr = vis_scope_colors[h];
+                        *(ptr + 1) = vis_scope_colors[h];
+                        *(ptr + 152) = vis_scope_colors[h];
+                        *(ptr + 153) = vis_scope_colors[h];
+                    }
+                    break;
+                case SCOPE_SOLID:
+                    h = 15 - vis->vs_data[x];
+                    h2 = 9;
+                    c = vis_scope_colors[(gint) vis->vs_data[x]];
+                    if (h > h2) {
+                        y = h;
+                        h = h2;
+                        h2 = y;
+                    }
+                    ptr = rgb_data + (h * 304) + (x << 1);
+                    for (y = h; y <= h2; y++, ptr += 304) {
+                        *ptr = c;
+                        *(ptr + 1) = c;
+                        *(ptr + 152) = c;
+                        *(ptr + 153) = c;
+                    }
+                    break;
+                }
+            }
+        }
 
-    /* FIXME: The check "shouldn't" be neccessary? */
-    /*	if (GTK_IS_WINDOW(vis->vs_window)) { */
-    GDK_THREADS_ENTER();
-    gdk_draw_indexed_image(vis->vs_window, vis->vs_widget.gc,
-                           vis->vs_widget.x, vis->vs_widget.y,
-                           vis->vs_widget.width, vis->vs_widget.height,
-                           GDK_RGB_DITHER_NORMAL, (guchar *) rgb_data,
-                           76, cmap);
-    GDK_THREADS_LEAVE();
-    /*	} else {
-        vis->vs_window = mainwin->window;
         GDK_THREADS_ENTER();
         gdk_draw_indexed_image(vis->vs_window, vis->vs_widget.gc,
-        vis->vs_widget.x, vis->vs_widget.y,
-        vis->vs_widget.width, vis->vs_widget.height,
-        GDK_RGB_DITHER_NORMAL, (guchar *) rgb_data,
-        76, cmap);
+                               vis->vs_widget.x << 1,
+                               vis->vs_widget.y << 1,
+                               vis->vs_widget.width << 1,
+                               vis->vs_widget.height << 1,
+                               GDK_RGB_DITHER_NONE, (guchar *) rgb_data,
+                               152, cmap);
         GDK_THREADS_LEAVE();
-        }
-    */
+    }
 
     gdk_rgb_cmap_free(cmap);
 }
@@ -259,11 +400,23 @@
 }
 
 void
+vis_set_doublesize(Vis * vis, gboolean doublesize)
+{
+    vis->vs_doublesize = doublesize;
+}
+
+void
 vis_clear(Vis * vis)
 {
-    gdk_window_clear_area(vis->vs_window, vis->vs_widget.x,
-                          vis->vs_widget.y, vis->vs_widget.width,
-                          vis->vs_widget.height);
+    if (!vis->vs_doublesize)
+        gdk_window_clear_area(vis->vs_window, vis->vs_widget.x,
+                              vis->vs_widget.y, vis->vs_widget.width,
+                              vis->vs_widget.height);
+    else
+        gdk_window_clear_area(vis->vs_window, vis->vs_widget.x << 1,
+                              vis->vs_widget.y << 1,
+                              vis->vs_widget.width << 1,
+                              vis->vs_widget.height << 1);
 }
 
 void
@@ -278,13 +431,17 @@
            GdkWindow * window,
            GdkGC * gc,
            gint x, gint y,
-           gint width)
+           gint width,
+	   gboolean doublesize)
 {
     Vis *vis;
 
     vis = g_new0(Vis, 1);
 
     widget_init(&vis->vs_widget, parent, gc, x, y, width, 16, 1);
+
+    vis->vs_doublesize = doublesize;
+
     widget_list_add(wlist, WIDGET(vis));
 
     return vis;
--- a/audacious/widgets/vis.h	Sun Nov 05 02:38:25 2006 -0800
+++ b/audacious/widgets/vis.h	Sun Nov 05 04:43:16 2006 -0800
@@ -66,6 +66,7 @@
     GdkWindow *vs_window;
     gfloat vs_data[75], vs_peak[75], vs_peak_speed[75];
     gint vs_refresh_delay;
+    gboolean vs_doublesize;
 };
 
 typedef struct _Vis Vis;
@@ -73,10 +74,11 @@
 void vis_draw(Widget * w);
 
 Vis *create_vis(GList ** wlist, GdkPixmap * parent, GdkWindow * window,
-                GdkGC * gc, gint x, gint y, gint width);
+                GdkGC * gc, gint x, gint y, gint width, gboolean doublesize);
 void vis_timeout_func(Vis * vis, guchar * data);
 void vis_clear_data(Vis * vis);
 void vis_clear(Vis * vis);
+void vis_set_doublesize(Vis * vis, gboolean doublesize);
 void vis_set_window(Vis * vis, GdkWindow * window);
 
 #endif