diff options
author | Eric Koegel <eric.koegel@gmail.com> | 2013-02-26 10:50:20 +0300 |
---|---|---|
committer | Eric Koegel <eric.koegel@gmail.com> | 2013-03-03 08:37:04 +0300 |
commit | 3cec6972530e4e4af47dbb84358fa8fedcc00f82 (patch) | |
tree | 010b4b6c31d5d17250608b1cdb1a5419f4458fc2 | |
parent | 8674fc7ea9e0acae40db69714be13054053ef44d (diff) | |
download | xfdesktop-3cec6972530e4e4af47dbb84358fa8fedcc00f82.tar.gz |
Fixes for multi-monitor per-workspace wallpapers
This fixes several issues with the per-workspace backdrop code,
especially with multi-monitor setups. Selection mode in the settings
app is set to browse to enforce an item is always selected. Also
xfdesktop trys to avoid redrawing the wallpaper on a workspace
change if the backdrops are identical. The --reload option works
correctly again.
-rw-r--r-- | settings/main.c | 113 | ||||
-rw-r--r-- | settings/xfdesktop-settings-appearance-frame-ui.glade | 1 | ||||
-rw-r--r-- | src/xfce-backdrop.c | 58 | ||||
-rw-r--r-- | src/xfce-backdrop.h | 3 | ||||
-rw-r--r-- | src/xfce-desktop.c | 114 | ||||
-rw-r--r-- | src/xfce-workspace.c | 81 |
6 files changed, 220 insertions, 150 deletions
diff --git a/settings/main.c b/settings/main.c index 441bcdc3..1308b21f 100644 --- a/settings/main.c +++ b/settings/main.c @@ -77,6 +77,8 @@ #define DESKTOP_ICONS_SHOW_FILESYSTEM "/desktop-icons/file-icons/show-filesystem" #define DESKTOP_ICONS_SHOW_REMOVABLE "/desktop-icons/file-icons/show-removable" +#define IMAGE_STLYE_SPANNING_SCREENS 6 +#define XFCE_BACKDROP_IMAGE_NONE 0 typedef struct { @@ -480,6 +482,8 @@ xfdesktop_settings_generate_per_workspace_binding_string(AppearancePanel *panel, property); } + DBG("name %s", buf); + return buf; } @@ -660,6 +664,21 @@ cb_folder_selection_changed(GtkWidget *button, } static void +cb_xfdesktop_combo_image_style_changed(GtkComboBox *combo, + gpointer user_data) +{ + AppearancePanel *panel = user_data; + + TRACE("entering"); + + if(gtk_combo_box_get_active(combo) == XFCE_BACKDROP_IMAGE_NONE) { + gtk_widget_set_sensitive(panel->image_iconview, FALSE); + } else { + gtk_widget_set_sensitive(panel->image_iconview, TRUE); + } +} + +static void cb_xfdesktop_combo_color_changed(GtkComboBox *combo, gpointer user_data) { @@ -723,6 +742,8 @@ xfdesktop_settings_background_tab_change_bindings(AppearancePanel *panel, } else { xfconf_g_property_bind(channel, buf, G_TYPE_INT, G_OBJECT(panel->image_style_combo), "active"); + /* determine if the iconview is sensitive */ + cb_xfdesktop_combo_image_style_changed(GTK_COMBO_BOX(panel->image_style_combo), panel); } g_free(buf); @@ -734,12 +755,15 @@ xfdesktop_settings_background_tab_change_bindings(AppearancePanel *panel, } else { xfconf_g_property_bind(channel, buf, G_TYPE_INT, G_OBJECT(panel->color_style_combo), "active"); + /* update the color button sensitivity */ + cb_xfdesktop_combo_color_changed(GTK_COMBO_BOX(panel->color_style_combo), panel); } g_free(buf); buf = xfdesktop_settings_generate_per_workspace_binding_string(panel, "color1"); if(remove_binding) { xfconf_g_property_unbind(panel->color1_btn_id); + } else { panel->color1_btn_id = xfconf_g_property_bind_gdkcolor(channel, buf, G_OBJECT(panel->color1_btn), "color"); @@ -756,9 +780,6 @@ xfdesktop_settings_background_tab_change_bindings(AppearancePanel *panel, } g_free(buf); - cb_xfdesktop_combo_color_changed(GTK_COMBO_BOX(panel->color_style_combo), - panel); - /* Cycle timer options */ buf = xfdesktop_settings_generate_per_workspace_binding_string(panel, "backdrop-cycle-enable"); if(remove_binding) { @@ -792,8 +813,6 @@ xfdesktop_settings_background_tab_change_bindings(AppearancePanel *panel, } g_free(buf); - cb_xfdesktop_chk_cycle_backdrop_toggled(GTK_CHECK_BUTTON(panel->backdrop_cycle_chkbox), - panel); } static void @@ -844,23 +863,24 @@ cb_update_background_tab(WnckWindow *wnck_window, panel->monitor = monitor_num; panel->monitor_name = gdk_screen_get_monitor_plug_name(screen, panel->monitor); + /* The first monitor has the option of doing the "spanning screens" style, + * but only if there's multiple monitors attached. Remove it in all other cases. + * + * Remove the spanning screens option before we potentially add it again + */ + gtk_combo_box_text_remove(GTK_COMBO_BOX_TEXT(panel->image_style_combo), + IMAGE_STLYE_SPANNING_SCREENS); + if(panel->monitor == 0 && gdk_screen_get_n_monitors(screen) > 1) { + gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(panel->image_style_combo), + _("Spanning screens")); + } + /* connect the new bindings */ xfdesktop_settings_background_tab_change_bindings(panel, FALSE); xfdesktop_settings_update_iconview_frame_name(panel, wnck_workspace); xfdesktop_settings_update_iconview_folder(panel); - - /* The first monitor has the option of doing the "spanning screens" style, - * but only if there's multiple monitors attached. Make it invisible - * in all other cases. - * Remove the spanning screens option before we potentially add it again - */ - gtk_combo_box_text_remove(GTK_COMBO_BOX_TEXT(panel->image_style_combo), 6); - if(panel->monitor == 0 && gdk_screen_get_n_monitors(screen) > 1) { - gtk_combo_box_text_insert_text(GTK_COMBO_BOX_TEXT(panel->image_style_combo), - 6, _("Spanning screens")); - } } static void @@ -874,6 +894,7 @@ xfdesktop_settings_setup_image_iconview(AppearancePanel *panel) "pixbuf-column", COL_PIX, "item-width", PREVIEW_WIDTH, "tooltip-column", COL_NAME, + "selection-mode", GTK_SELECTION_BROWSE, NULL); g_signal_connect(G_OBJECT(iconview), "selection-changed", @@ -883,7 +904,8 @@ xfdesktop_settings_setup_image_iconview(AppearancePanel *panel) static void xfdesktop_settings_dialog_setup_tabs(GtkBuilder *main_gxml, XfconfChannel *channel, - GdkScreen *screen) + GdkScreen *screen, + gulong window_xid) { GtkWidget *appearance_container, *chk_custom_font_size, *spin_font_size, *w, *box, *spin_icon_size, @@ -944,7 +966,10 @@ xfdesktop_settings_dialog_setup_tabs(GtkBuilder *main_gxml, /* We have to force wnck to initialize */ wnck_screen = wnck_screen_get(panel->screen); wnck_screen_force_update(wnck_screen); - wnck_window = wnck_window_get(GDK_WINDOW_XID(gtk_widget_get_window(appearance_container))); + wnck_window = wnck_window_get(window_xid); + + if(wnck_window == NULL) + wnck_window = wnck_screen_get_active_window(wnck_screen); g_signal_connect(wnck_window, "geometry-changed", G_CALLBACK(cb_update_background_tab), panel); @@ -975,25 +1000,6 @@ xfdesktop_settings_dialog_setup_tabs(GtkBuilder *main_gxml, gtk_table_attach_defaults(GTK_TABLE(appearance_container), appearance_settings, 0,1,0,1); - panel->image_style_combo = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, "combo_style")); - - panel->color_style_combo = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, - "combo_colors")); - - /* Pick the first entries so something shows up */ - gtk_combo_box_set_active(GTK_COMBO_BOX(panel->image_style_combo), 0); - gtk_combo_box_set_active(GTK_COMBO_BOX(panel->color_style_combo), 0); - - g_signal_connect(G_OBJECT(panel->color_style_combo), "changed", - G_CALLBACK(cb_xfdesktop_combo_color_changed), - panel); - - panel->color1_btn = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, - "color1_btn")); - - panel->color2_btn = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, - "color2_btn")); - /* icon view area */ panel->frame_image_list = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, "frame_image_list")); @@ -1012,6 +1018,30 @@ xfdesktop_settings_dialog_setup_tabs(GtkBuilder *main_gxml, gtk_file_filter_add_pixbuf_formats(filter); gtk_file_chooser_add_filter(GTK_FILE_CHOOSER(panel->btn_folder), filter); + /* Image and color style options */ + panel->image_style_combo = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, "combo_style")); + + panel->color_style_combo = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, + "combo_colors")); + + panel->color1_btn = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, + "color1_btn")); + + panel->color2_btn = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, + "color2_btn")); + + g_signal_connect(G_OBJECT(panel->image_style_combo), "changed", + G_CALLBACK(cb_xfdesktop_combo_image_style_changed), + panel); + + g_signal_connect(G_OBJECT(panel->color_style_combo), "changed", + G_CALLBACK(cb_xfdesktop_combo_color_changed), + panel); + + /* Pick the first entries so something shows up */ + gtk_combo_box_set_active(GTK_COMBO_BOX(panel->image_style_combo), 0); + gtk_combo_box_set_active(GTK_COMBO_BOX(panel->color_style_combo), 0); + /* background cycle timer */ panel->backdrop_cycle_chkbox = GTK_WIDGET(gtk_builder_get_object(appearance_gxml, "chk_cycle_backdrop")); @@ -1094,6 +1124,7 @@ xfdesktop_settings_dialog_setup_tabs(GtkBuilder *main_gxml, "active"); setup_special_icon_list(main_gxml, channel); + cb_update_background_tab(wnck_window, panel); } static void @@ -1175,7 +1206,8 @@ main(int argc, char **argv) G_CALLBACK(xfdesktop_settings_response), NULL); gtk_window_present(GTK_WINDOW (dialog)); xfdesktop_settings_dialog_setup_tabs(gxml, channel, - gtk_widget_get_screen(dialog)); + gtk_widget_get_screen(dialog), + GDK_WINDOW_XID(gtk_widget_get_window(dialog))); /* To prevent the settings dialog to be saved in the session */ gdk_x11_set_sm_client_id("FAKE ID"); @@ -1188,14 +1220,15 @@ main(int argc, char **argv) gtk_widget_show(plug); g_signal_connect(G_OBJECT(plug), "delete-event", G_CALLBACK(gtk_main_quit), NULL); - xfdesktop_settings_dialog_setup_tabs(gxml, channel, - gtk_widget_get_screen(plug)); gdk_notify_startup_complete(); plug_child = GTK_WIDGET(gtk_builder_get_object(gxml, "alignment1")); gtk_widget_reparent(plug_child, plug); gtk_widget_show(plug_child); + xfdesktop_settings_dialog_setup_tabs(gxml, channel, + gtk_widget_get_screen(plug), + GDK_WINDOW_XID(gtk_widget_get_window(plug_child))); gtk_main(); } diff --git a/settings/xfdesktop-settings-appearance-frame-ui.glade b/settings/xfdesktop-settings-appearance-frame-ui.glade index 9a5ac568..ee8e334e 100644 --- a/settings/xfdesktop-settings-appearance-frame-ui.glade +++ b/settings/xfdesktop-settings-appearance-frame-ui.glade @@ -117,6 +117,7 @@ <item translatable="yes">Stretched</item> <item translatable="yes">Scaled</item> <item translatable="yes">Zoomed</item> + <item translatable="yes">Spanning Screens</item> </items> </object> <packing> diff --git a/src/xfce-backdrop.c b/src/xfce-backdrop.c index 4b3a9097..1a634268 100644 --- a/src/xfce-backdrop.c +++ b/src/xfce-backdrop.c @@ -296,13 +296,6 @@ xfce_backdrop_class_init(XfceBackdropClass *klass) DEFAULT_BACKDROP, XFDESKTOP_PARAM_FLAGS)); - g_object_class_install_property(gobject_class, PROP_BRIGHTNESS, - g_param_spec_int("brightness", - "brightness", - "brightness", - -128, 127, 0, - XFDESKTOP_PARAM_FLAGS)); - g_object_class_install_property(gobject_class, PROP_BACKDROP_CYCLE_ENABLE, g_param_spec_boolean("backdrop-cycle-enable", "backdrop-cycle-enable", @@ -742,7 +735,9 @@ xfce_backdrop_timer(XfceBackdrop *backdrop) g_return_val_if_fail(XFCE_IS_BACKDROP(backdrop), FALSE); - g_signal_emit(G_OBJECT(backdrop), backdrop_signals[BACKDROP_CYCLE], 0); + /* Don't bother with trying to cycle a backdrop if we're not using images */ + if(backdrop->priv->image_style != XFCE_BACKDROP_IMAGE_NONE) + g_signal_emit(G_OBJECT(backdrop), backdrop_signals[BACKDROP_CYCLE], 0); return TRUE; } @@ -881,7 +876,8 @@ xfce_backdrop_get_pixbuf(XfceBackdrop *backdrop) /*check if the file exists, *and if it doesn't then make the background the single colour*/ - if(!g_file_test(backdrop->priv->image_path, G_FILE_TEST_EXISTS)) { + if(!g_file_test(backdrop->priv->image_path, G_FILE_TEST_EXISTS) || + backdrop->priv->image_style == XFCE_BACKDROP_IMAGE_NONE) { if(backdrop->priv->brightness != 0) final_image = adjust_brightness(final_image, backdrop->priv->brightness); @@ -926,6 +922,12 @@ xfce_backdrop_get_pixbuf(XfceBackdrop *backdrop) case XFCE_BACKDROP_IMAGE_TILED: image = gdk_pixbuf_new_from_file(backdrop->priv->image_path, NULL); tmp = gdk_pixbuf_new(GDK_COLORSPACE_RGB, TRUE, 8, w, h); + /* Now that the image has been loaded, recalculate the image + * size because gdk_pixbuf_get_file_info doesn't always return + * the correct size */ + iw = gdk_pixbuf_get_width(image); + ih = gdk_pixbuf_get_height(image); + for(i = 0; (i * iw) < w; i++) { for(j = 0; (j * ih) < h; j++) { gint newx = iw * i, newy = ih * j; @@ -935,7 +937,7 @@ xfce_backdrop_get_pixbuf(XfceBackdrop *backdrop) neww = w - newx; if((newy + newh) > h) newh = h - newy; - + gdk_pixbuf_copy_area(image, 0, 0, neww, newh, tmp, newx, newy); } @@ -947,7 +949,6 @@ xfce_backdrop_get_pixbuf(XfceBackdrop *backdrop) break; case XFCE_BACKDROP_IMAGE_STRETCHED: - case XFCE_BACKDROP_IMAGE_SPANNING_SCREENS: image = gdk_pixbuf_new_from_file_at_scale( backdrop->priv->image_path, w, h, FALSE, NULL); gdk_pixbuf_composite(image, final_image, 0, 0, w, h, @@ -978,6 +979,7 @@ xfce_backdrop_get_pixbuf(XfceBackdrop *backdrop) break; case XFCE_BACKDROP_IMAGE_ZOOMED: + case XFCE_BACKDROP_IMAGE_SPANNING_SCREENS: xscale = (gdouble)w / iw; yscale = (gdouble)h / ih; if(xscale < yscale) { @@ -1009,3 +1011,37 @@ xfce_backdrop_get_pixbuf(XfceBackdrop *backdrop) return final_image; } + +/* returns TRUE if they have identical settings. */ +gboolean xfce_backdrop_compare_backdrops(XfceBackdrop *backdrop_a, + XfceBackdrop *backdrop_b) +{ + if(g_strcmp0(backdrop_a->priv->image_path, backdrop_b->priv->image_path) != 0) { + DBG("filename different"); + return FALSE; + } + + if(backdrop_a->priv->image_style != backdrop_b->priv->image_style) { + DBG("image_style different"); + return FALSE; + } + + if(backdrop_a->priv->color_style != backdrop_b->priv->color_style) { + DBG("color_style different"); + return FALSE; + } + + if(!gdk_color_equal(&backdrop_a->priv->color1, &backdrop_b->priv->color1) || + !gdk_color_equal(&backdrop_a->priv->color2, &backdrop_b->priv->color2)) { + DBG("colors different"); + return FALSE; + } + + if(backdrop_a->priv->cycle_backdrop != backdrop_b->priv->cycle_backdrop || + backdrop_a->priv->cycle_backdrop == TRUE) { + DBG("backdrop cycle different"); + return FALSE; + } + + return TRUE; +} diff --git a/src/xfce-backdrop.h b/src/xfce-backdrop.h index 6c013c35..fbb01a9e 100644 --- a/src/xfce-backdrop.h +++ b/src/xfce-backdrop.h @@ -130,6 +130,9 @@ gboolean xfce_backdrop_get_random_order (XfceBackdrop *backdrop); GdkPixbuf *xfce_backdrop_get_pixbuf (XfceBackdrop *backdrop); +gboolean xfce_backdrop_compare_backdrops (XfceBackdrop *backdrop_a, + XfceBackdrop *backdrop_b); + G_END_DECLS #endif diff --git a/src/xfce-desktop.c b/src/xfce-desktop.c index 95c30f6d..6e124562 100644 --- a/src/xfce-desktop.c +++ b/src/xfce-desktop.c @@ -336,11 +336,6 @@ backdrop_changed_cb(XfceBackdrop *backdrop, gpointer user_data) DBG("backdrop changed for workspace %d, monitor %d (%s)", current_workspace, monitor, gdk_screen_get_monitor_plug_name(gscreen, monitor)); - /* create/get the composited backdrop pixmap */ - pix = xfce_backdrop_get_pixbuf(backdrop); - if(!pix) - return; - if(xfce_desktop_get_n_monitors(desktop) > 1 && xfce_workspace_get_xinerama_stretch(desktop->priv->workspaces[current_workspace])) { GdkRectangle monitor_rect; @@ -360,10 +355,21 @@ backdrop_changed_cb(XfceBackdrop *backdrop, gpointer user_data) rect.width = gdk_screen_get_width(gscreen); rect.height = gdk_screen_get_height(gscreen); + DBG("xinerama_stretch x %d, y %d, width %d, height %d", + rect.x, rect.y, rect.width, rect.height); } else { gdk_screen_get_monitor_geometry(gscreen, monitor, &rect); + DBG("monitor x %d, y %d, width %d, height %d", + rect.x, rect.y, rect.width, rect.height); } + xfce_backdrop_set_size(backdrop, rect.width, rect.height); + + /* create/get the composited backdrop pixmap */ + pix = xfce_backdrop_get_pixbuf(backdrop); + if(!pix) + return; + cr = gdk_cairo_create(GDK_DRAWABLE(pmap)); gdk_cairo_set_source_pixbuf(cr, pix, rect.x, rect.y); cairo_paint(cr); @@ -415,17 +421,12 @@ screen_size_changed_cb(GdkScreen *gscreen, gpointer user_data) /* special case for 1 backdrop to handle xinerama stretching */ if(xfce_workspace_get_xinerama_stretch(desktop->priv->workspaces[current_workspace])) { - xfce_backdrop_set_size(xfce_workspace_get_backdrop(desktop->priv->workspaces[current_workspace], 0), w, h); backdrop_changed_cb(xfce_workspace_get_backdrop(desktop->priv->workspaces[current_workspace], 0), desktop); } else { - GdkRectangle rect; gint i; for(i = 0; i < xfce_desktop_get_n_monitors(desktop); i++) { - gdk_screen_get_monitor_geometry(gscreen, i, &rect); current_backdrop = xfce_workspace_get_backdrop(desktop->priv->workspaces[current_workspace], i); - - xfce_backdrop_set_size(current_backdrop, rect.width, rect.height); backdrop_changed_cb(current_backdrop, desktop); } } @@ -481,13 +482,37 @@ workspace_changed_cb(WnckScreen *wnck_screen, { XfceDesktop *desktop = XFCE_DESKTOP(user_data); WnckWorkspace *wnck_workspace = wnck_screen_get_active_workspace(wnck_screen); + gint current_workspace, new_workspace, i; + XfceBackdrop *current_backdrop, *new_backdrop; TRACE("entering"); - desktop->priv->current_workspace = wnck_workspace_get_number(wnck_workspace); + current_workspace = desktop->priv->current_workspace; + new_workspace = wnck_workspace_get_number(wnck_workspace); + desktop->priv->current_workspace = new_workspace; - /* fake a screen size changed, so the background is properly set */ - screen_size_changed_cb(desktop->priv->gscreen, user_data); + /* special case for the spanning screen option */ + if(xfce_workspace_get_xinerama_stretch(desktop->priv->workspaces[new_workspace])) { + current_backdrop = xfce_workspace_get_backdrop(desktop->priv->workspaces[current_workspace], 0); + new_backdrop = xfce_workspace_get_backdrop(desktop->priv->workspaces[new_workspace], 0); + + if(!xfce_backdrop_compare_backdrops(current_backdrop, new_backdrop)) { + backdrop_changed_cb(new_backdrop, user_data); + return; + } + } + + /* We want to compare the current workspace backdrops with the new one + * and see if we can avoid changing them if they are the same image/style */ + for(i = 0; i < xfce_desktop_get_n_monitors(desktop); i++) { + current_backdrop = xfce_workspace_get_backdrop(desktop->priv->workspaces[current_workspace], i); + new_backdrop = xfce_workspace_get_backdrop(desktop->priv->workspaces[new_workspace], i); + + if(!xfce_backdrop_compare_backdrops(current_backdrop, new_backdrop)) { + /* only update monitors that require it */ + backdrop_changed_cb(new_backdrop, user_data); + } + } } static void @@ -1088,46 +1113,6 @@ xfce_desktop_connect_settings(XfceDesktop *desktop) xfce_desktop_thaw_updates(desktop); } -static void -xfce_desktop_image_filename_changed(XfconfChannel *channel, - const gchar *property, - const GValue *value, - gpointer user_data) -{ - XfceDesktop *desktop = user_data; - gchar *p; - const gchar *filename; - gint monitor, current_workspace; - XfceBackdrop *backdrop; - - TRACE("entering"); - - p = strstr(property, "/monitor"); - if(!p) - return; - - monitor = atoi(p + 8); - if(monitor < 0 || monitor >= xfce_desktop_get_n_monitors(desktop)) - return; - - current_workspace = desktop->priv->current_workspace; - - if(xfce_workspace_get_xinerama_stretch(desktop->priv->workspaces[current_workspace]) - && monitor != 0) - return; - - backdrop = xfce_workspace_get_backdrop(desktop->priv->workspaces[current_workspace], - monitor); - - if(!G_VALUE_HOLDS_STRING(value)) - filename = DEFAULT_BACKDROP; - else - filename = g_value_get_string(value); - - if(G_LIKELY(filename && *filename)) - xfce_backdrop_set_image_filename(backdrop, filename); -} - static gint xfce_desktop_get_current_workspace(XfceDesktop *desktop) { @@ -1394,8 +1379,7 @@ xfce_desktop_popup_secondary_root_menu(XfceDesktop *desktop, void xfce_desktop_refresh(XfceDesktop *desktop) { - gchar buf[256]; - gint i, max, current_workspace; + gint i, current_workspace; g_return_if_fail(XFCE_IS_DESKTOP(desktop)); @@ -1404,23 +1388,13 @@ xfce_desktop_refresh(XfceDesktop *desktop) current_workspace = desktop->priv->current_workspace; - /* reload image */ - if(xfce_workspace_get_xinerama_stretch(desktop->priv->workspaces[current_workspace])) - max = 1; - else - max = xfce_desktop_get_n_monitors(desktop); - for(i = 0; i < max; ++i) { - GValue val = { 0, }; - - g_snprintf(buf, sizeof(buf), "%smonitor%d/workspace%d/last-image", - desktop->priv->property_prefix, i, current_workspace); - xfconf_channel_get_property(desktop->priv->channel, buf, &val); + /* reload backgrounds */ + for(i = 0; i < xfce_desktop_get_n_monitors(desktop); i++) { + XfceBackdrop *backdrop; - xfce_desktop_image_filename_changed(desktop->priv->channel, buf, - &val, desktop); + backdrop = xfce_workspace_get_backdrop(desktop->priv->workspaces[current_workspace], i); - if(G_VALUE_TYPE(&val)) - g_value_unset(&val); + backdrop_changed_cb(backdrop, desktop); } #ifdef ENABLE_DESKTOP_ICONS diff --git a/src/xfce-workspace.c b/src/xfce-workspace.c index ba9f3278..1775fe94 100644 --- a/src/xfce-workspace.c +++ b/src/xfce-workspace.c @@ -82,6 +82,7 @@ struct _XfceWorkspacePriv guint workspace_num; guint nbackdrops; + gboolean xinerama_stretch; XfceBackdrop **backdrops; }; @@ -155,7 +156,28 @@ backdrop_cycle_cb(XfceBackdrop *backdrop, gpointer user_data) static void backdrop_changed_cb(XfceBackdrop *backdrop, gpointer user_data) { + XfceWorkspace *workspace = XFCE_WORKSPACE(user_data); TRACE("entering"); + + /* if we were spanning all the screens and we're not doing it anymore + * we need to update all the backdrops for this workspace */ + if(workspace->priv->xinerama_stretch == TRUE && + xfce_workspace_get_xinerama_stretch(workspace) == FALSE) { + guint i; + + for(i = 0; i < workspace->priv->nbackdrops; ++i) { + /* skip the current backdrop, we'll get it last */ + if(workspace->priv->backdrops[i] != backdrop) { + g_signal_emit(G_OBJECT(user_data), + signals[WORKSPACE_BACKDROP_CHANGED], + 0, + workspace->priv->backdrops[i]); + } + } + } + + workspace->priv->xinerama_stretch = xfce_workspace_get_xinerama_stretch(workspace); + /* Propagate it up */ g_signal_emit(G_OBJECT(user_data), signals[WORKSPACE_BACKDROP_CHANGED], 0, backdrop); } @@ -200,36 +222,35 @@ xfce_workspace_monitors_changed(XfceWorkspace *workspace, } else { /* We need one backdrop per monitor */ guint n_monitors = gdk_screen_get_n_monitors(gscreen); - - if(n_monitors < workspace->priv->nbackdrops) { - for(i = n_monitors; i < workspace->priv->nbackdrops; ++i) - g_object_unref(G_OBJECT(workspace->priv->backdrops[i])); - } - - if(n_monitors != workspace->priv->nbackdrops) { - workspace->priv->backdrops = g_realloc(workspace->priv->backdrops, - sizeof(XfceBackdrop *) * n_monitors); - if(n_monitors > workspace->priv->nbackdrops) { - GdkVisual *vis = gdk_screen_get_rgba_visual(gscreen); - if(vis == NULL) - vis = gdk_screen_get_system_visual(gscreen); - - for(i = workspace->priv->nbackdrops; i < n_monitors; ++i) { - workspace->priv->backdrops[i] = xfce_backdrop_new(vis); - xfce_workspace_connect_backdrop_settings(workspace, - workspace->priv->backdrops[i], - i); - g_signal_connect(G_OBJECT(workspace->priv->backdrops[0]), - "changed", - G_CALLBACK(backdrop_changed_cb), workspace); - g_signal_connect(G_OBJECT(workspace->priv->backdrops[i]), - "cycle", - G_CALLBACK(backdrop_cycle_cb), - workspace); - } - } - workspace->priv->nbackdrops = n_monitors; + GdkVisual *vis = gdk_screen_get_rgba_visual(gscreen); + + if(vis == NULL) + vis = gdk_screen_get_system_visual(gscreen); + + /* Remove all backdrops so that the correct montior is added/removed and + * things stay in the correct order */ + for(i = 0; i < workspace->priv->nbackdrops; ++i) + g_object_unref(G_OBJECT(workspace->priv->backdrops[i])); + + workspace->priv->backdrops = g_realloc(workspace->priv->backdrops, + sizeof(XfceBackdrop *) * n_monitors); + + for(i = 0; i < n_monitors; ++i) { + DBG("Adding workspace %d backdrop %d", workspace->priv->workspace_num, i); + + workspace->priv->backdrops[i] = xfce_backdrop_new(vis); + xfce_workspace_connect_backdrop_settings(workspace, + workspace->priv->backdrops[i], + i); + g_signal_connect(G_OBJECT(workspace->priv->backdrops[i]), + "changed", + G_CALLBACK(backdrop_changed_cb), workspace); + g_signal_connect(G_OBJECT(workspace->priv->backdrops[i]), + "cycle", + G_CALLBACK(backdrop_cycle_cb), + workspace); } + workspace->priv->nbackdrops = n_monitors; } } @@ -321,6 +342,8 @@ xfce_workspace_connect_backdrop_settings(XfceWorkspace *workspace, } pp_len = strlen(buf); + DBG("prefix string: %s", buf); + g_strlcat(buf, "color-style", sizeof(buf)); xfconf_g_property_bind(channel, buf, XFCE_TYPE_BACKDROP_COLOR_STYLE, G_OBJECT(backdrop), "color-style"); |