diff options
| author | Victor Kareh <[email protected]> | 2026-07-09 15:19:30 -0400 |
|---|---|---|
| committer | Luke from DC <[email protected]> | 2026-07-27 23:15:29 +0000 |
| commit | 1da140c5e95d382dfe60d6a80ef28d18afbabe06 (patch) | |
| tree | 864dafb1bc4f94784550f60fa98d477a032906ab | |
| parent | 59d1bf98a3d37819b65dc780cca22c2cf38260be (diff) | |
| download | mate-panel-1da140c5e95d382dfe60d6a80ef28d18afbabe06.tar.bz2 mate-panel-1da140c5e95d382dfe60d6a80ef28d18afbabe06.tar.xz | |
panel: Move to a model where panel objects are all packed
Instead of positioning objects on specific positions on panels, we pack
them all either at the start or the end. This simplifies things a lot, and
helps keep clean panels.
Note that adding/moving objects is broken right now.
For backward compatibility the old position key is still read and used
as a fallback.
Backported from https://gitlab.gnome.org/GNOME/gnome-panel/-/commit/6db6be277
| -rw-r--r-- | data/org.mate.panel.object.gschema.xml.in | 5 | ||||
| -rw-r--r-- | mate-panel/applet.c | 69 | ||||
| -rw-r--r-- | mate-panel/applet.h | 4 | ||||
| -rw-r--r-- | mate-panel/drawer-private.h | 1 | ||||
| -rw-r--r-- | mate-panel/drawer.c | 9 | ||||
| -rw-r--r-- | mate-panel/drawer.h | 1 | ||||
| -rw-r--r-- | mate-panel/launcher.c | 7 | ||||
| -rw-r--r-- | mate-panel/launcher.h | 1 | ||||
| -rw-r--r-- | mate-panel/panel-action-button.c | 8 | ||||
| -rw-r--r-- | mate-panel/panel-action-button.h | 1 | ||||
| -rw-r--r-- | mate-panel/panel-applet-frame.c | 38 | ||||
| -rw-r--r-- | mate-panel/panel-applet-frame.h | 1 | ||||
| -rw-r--r-- | mate-panel/panel-layout.c | 1 | ||||
| -rw-r--r-- | mate-panel/panel-menu-bar.c | 10 | ||||
| -rw-r--r-- | mate-panel/panel-menu-bar.h | 1 | ||||
| -rw-r--r-- | mate-panel/panel-menu-button.c | 7 | ||||
| -rw-r--r-- | mate-panel/panel-menu-button.h | 1 | ||||
| -rw-r--r-- | mate-panel/panel-profile.c | 13 | ||||
| -rw-r--r-- | mate-panel/panel-profile.h | 6 | ||||
| -rw-r--r-- | mate-panel/panel-schemas.h | 1 | ||||
| -rw-r--r-- | mate-panel/panel-separator.c | 5 | ||||
| -rw-r--r-- | mate-panel/panel-separator.h | 1 | ||||
| -rw-r--r-- | mate-panel/panel-widget.c | 244 | ||||
| -rw-r--r-- | mate-panel/panel-widget.h | 13 |
24 files changed, 346 insertions, 102 deletions
diff --git a/data/org.mate.panel.object.gschema.xml.in b/data/org.mate.panel.object.gschema.xml.in index b5cc6ae7..1af53d89 100644 --- a/data/org.mate.panel.object.gschema.xml.in +++ b/data/org.mate.panel.object.gschema.xml.in @@ -15,6 +15,11 @@ <summary>Interpret position relative to bottom/right edge</summary> <description>If set to 'end', the position of the object is interpreted relative to the right (or bottom if vertical) edge of the panel.</description> </key> + <key name="pack-index" type="i"> + <default>0</default> + <summary>Object's position on the panel</summary> + <description>The position of this panel object. The position is specified by the number of pixels from the left (or top if vertical) panel edge.</description> + </key> <key name="position" type="i"> <default>0</default> <summary>Object's position on the panel (deprecated)</summary> diff --git a/mate-panel/applet.c b/mate-panel/applet.c index ee9d3112..9f666392 100644 --- a/mate-panel/applet.c +++ b/mate-panel/applet.c @@ -769,6 +769,7 @@ typedef struct { char *toplevel_id; int position; PanelObjectPackType pack_type; + int pack_index; guint locked : 1; } MatePanelAppletToLoad; @@ -907,6 +908,7 @@ mate_panel_applet_load_idle_handler (gpointer dummy) applet->locked, applet->position, applet->pack_type, + applet->pack_index, applet->id); break; case PANEL_OBJECT_DRAWER: @@ -914,6 +916,7 @@ mate_panel_applet_load_idle_handler (gpointer dummy) applet->locked, applet->position, applet->pack_type, + applet->pack_index, applet->id); break; case PANEL_OBJECT_MENU: @@ -921,6 +924,7 @@ mate_panel_applet_load_idle_handler (gpointer dummy) applet->locked, applet->position, applet->pack_type, + applet->pack_index, TRUE, applet->id); break; @@ -929,6 +933,7 @@ mate_panel_applet_load_idle_handler (gpointer dummy) applet->locked, applet->position, applet->pack_type, + applet->pack_index, applet->id); break; case PANEL_OBJECT_ACTION: @@ -937,6 +942,7 @@ mate_panel_applet_load_idle_handler (gpointer dummy) applet->locked, applet->position, applet->pack_type, + applet->pack_index, TRUE, applet->id); break; @@ -946,6 +952,7 @@ mate_panel_applet_load_idle_handler (gpointer dummy) applet->locked, applet->position, applet->pack_type, + applet->pack_index, TRUE, applet->id); break; @@ -954,6 +961,7 @@ mate_panel_applet_load_idle_handler (gpointer dummy) applet->locked, applet->position, applet->pack_type, + applet->pack_index, applet->id); break; default: @@ -974,6 +982,7 @@ mate_panel_applet_queue_applet_to_load (const char *id, const char *toplevel_id, int position, PanelObjectPackType pack_type, + int pack_index, gboolean locked) { MatePanelAppletToLoad *applet; @@ -990,6 +999,7 @@ mate_panel_applet_queue_applet_to_load (const char *id, applet->toplevel_id = g_strdup (toplevel_id); applet->position = position; applet->pack_type = pack_type; + applet->pack_index = pack_index; applet->locked = locked != FALSE; mate_panel_applets_to_load = g_slist_prepend (mate_panel_applets_to_load, applet); @@ -1005,7 +1015,14 @@ mate_panel_applet_compare (const MatePanelAppletToLoad *a, return c; else if (a->pack_type != b->pack_type) return a->pack_type - b->pack_type; /* start < center < end */ + else if (a->pack_index != b->pack_index) + /* note: for packed-end, we explicitly want to start loading + * from the right/bottom instead of left/top to avoid moving + * applets that are on the inside; so the maths are good even + * in this case */ + return a->pack_index - b->pack_index; else + /* Fallback to pixel position in case all pack_index are 0. */ return a->position - b->position; } @@ -1086,11 +1103,10 @@ mate_panel_applet_save_position (AppletInfo *applet_info, gboolean immediate) { PanelWidget *panel_widget; + AppletData *applet_data; const char *toplevel_id; char *old_toplevel_id; - gboolean right_stick; gboolean locked; - int position; g_return_if_fail (applet_info != NULL); @@ -1112,9 +1128,8 @@ mate_panel_applet_save_position (AppletInfo *applet_info, return; panel_widget = mate_panel_applet_get_panel_widget (applet_info); - - /* FIXME: Instead of getting keys, comparing and setting, there - should be a dirty flag */ + applet_data = g_object_get_data (G_OBJECT (applet_info->widget), + MATE_PANEL_APPLET_DATA); old_toplevel_id = g_settings_get_string (applet_info->settings, PANEL_OBJECT_TOPLEVEL_ID_KEY); if (old_toplevel_id == NULL || strcmp (old_toplevel_id, toplevel_id) != 0) @@ -1122,33 +1137,22 @@ mate_panel_applet_save_position (AppletInfo *applet_info, g_free (old_toplevel_id); /* Note: changing some properties of the panel that may not be locked down - (e.g. background) can change the state of the "panel_right_stick" and - "position" properties of an applet that may in fact be locked down. + (e.g. background) can change the state of the "pack-type" and + "pack-index" properties of an applet that may in fact be locked down. So check if these are writable before attempting to write them */ locked = panel_widget_get_applet_locked (panel_widget, applet_info->widget) ? 1 : 0; if (g_settings_get_boolean (applet_info->settings, PANEL_OBJECT_LOCKED_KEY) ? 1 : 0 != locked) g_settings_set_boolean (applet_info->settings, PANEL_OBJECT_LOCKED_KEY, locked); - if (locked) { - /* Until position calculations are refactored to fix the issue of the panel applets - getting reordered on resolution changes... - .. don't save position/right-stick on locked applets */ - return; - } - - right_stick = panel_is_applet_right_stick (applet_info->widget) ? 1 : 0; - if (g_settings_is_writable (applet_info->settings, PANEL_OBJECT_PANEL_RIGHT_STICK_KEY) && - (g_settings_get_boolean (applet_info->settings, PANEL_OBJECT_PANEL_RIGHT_STICK_KEY) ? 1 : 0) != right_stick) - g_settings_set_boolean (applet_info->settings, PANEL_OBJECT_PANEL_RIGHT_STICK_KEY, right_stick); - - position = mate_panel_applet_get_position (applet_info); - if (right_stick && !panel_widget->packed) - position = panel_widget->size - position; - - if (g_settings_is_writable (applet_info->settings, PANEL_OBJECT_POSITION_KEY) && - g_settings_get_int (applet_info->settings, PANEL_OBJECT_POSITION_KEY) != position) - g_settings_set_int (applet_info->settings, PANEL_OBJECT_POSITION_KEY, position); + if (g_settings_is_writable (applet_info->settings, PANEL_OBJECT_PACK_TYPE_KEY)) + g_settings_set_enum (applet_info->settings, + PANEL_OBJECT_PACK_TYPE_KEY, + applet_data->pack_type); + if (g_settings_is_writable (applet_info->settings, PANEL_OBJECT_PACK_INDEX_KEY)) + g_settings_set_int (applet_info->settings, + PANEL_OBJECT_PACK_INDEX_KEY, + applet_data->pack_index); } const char * @@ -1227,6 +1231,7 @@ mate_panel_applet_register (GtkWidget *applet, gboolean locked, gint pos, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, PanelObjectType type, const char *id) @@ -1288,14 +1293,14 @@ mate_panel_applet_register (GtkWidget *applet, registered_applets = g_slist_append (registered_applets, info); - if (panel_widget_add (panel, applet, locked, pos, pack_type, exactpos) == -1 && - panel_widget_add (panel, applet, locked, 0, PANEL_OBJECT_PACK_START, FALSE) == -1) { + if (panel_widget_add (panel, applet, locked, pos, pack_type, pack_index, exactpos) == -1 && + panel_widget_add (panel, applet, locked, 0, PANEL_OBJECT_PACK_START, 0, FALSE) == -1) { GSList *l; for (l = panels; l; l = l->next) { panel = PANEL_WIDGET (l->data); - if (panel_widget_add (panel, applet, locked, 0, PANEL_OBJECT_PACK_START, FALSE) != -1) + if (panel_widget_add (panel, applet, locked, 0, PANEL_OBJECT_PACK_START, 0, FALSE) != -1) break; } @@ -1356,13 +1361,13 @@ mate_panel_applet_can_freely_move (AppletInfo *applet) if (panel_lockdown_get_locked_down ()) return FALSE; - if (!g_settings_is_writable (applet->settings, PANEL_OBJECT_POSITION_KEY)) + if (!g_settings_is_writable (applet->settings, PANEL_OBJECT_PACK_TYPE_KEY)) return FALSE; - if (!g_settings_is_writable (applet->settings, PANEL_OBJECT_TOPLEVEL_ID_KEY)) + if (!g_settings_is_writable (applet->settings, PANEL_OBJECT_PACK_INDEX_KEY)) return FALSE; - if (!g_settings_is_writable (applet->settings, PANEL_OBJECT_PANEL_RIGHT_STICK_KEY)) + if (!g_settings_is_writable (applet->settings, PANEL_OBJECT_TOPLEVEL_ID_KEY)) return FALSE; return TRUE; diff --git a/mate-panel/applet.h b/mate-panel/applet.h index fc6b8108..804d9fba 100644 --- a/mate-panel/applet.h +++ b/mate-panel/applet.h @@ -54,6 +54,7 @@ AppletInfo *mate_panel_applet_register (GtkWidget *applet, gboolean locked, gint pos, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, PanelObjectType type, const char *id); @@ -73,6 +74,7 @@ void mate_panel_applet_queue_applet_to_load (const char *id, const char *toplevel_id, int position, PanelObjectPackType pack_type, + int pack_index, gboolean locked); void mate_panel_applet_load_queued_applets (gboolean initial_load); gboolean mate_panel_applet_on_load_queue (const char *id); @@ -95,7 +97,7 @@ void mate_panel_applet_save_position (AppletInfo *applet_info, int mate_panel_applet_get_position (AppletInfo *applet); /* True if all the keys relevant to moving are writable - (position, toplevel_id, panel_right_stick) */ + (pack_type, pack_index, toplevel_id) */ gboolean mate_panel_applet_can_freely_move (AppletInfo *applet); /* True if the locked flag is writable */ diff --git a/mate-panel/drawer-private.h b/mate-panel/drawer-private.h index f921ca9a..bc067229 100644 --- a/mate-panel/drawer-private.h +++ b/mate-panel/drawer-private.h @@ -129,6 +129,7 @@ static void load_drawer_applet (char *toplevel_id, gboolean locked, int pos, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id); diff --git a/mate-panel/drawer.c b/mate-panel/drawer.c index 3c5741a4..677d0734 100644 --- a/mate-panel/drawer.c +++ b/mate-panel/drawer.c @@ -493,6 +493,7 @@ load_drawer_applet (char *toplevel_id, gboolean locked, int pos, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id) { @@ -527,7 +528,7 @@ load_drawer_applet (char *toplevel_id, drawer->info = mate_panel_applet_register (drawer->button, drawer, (GDestroyNotify) g_free, panel_widget, - locked, pos, pack_type, exactpos, + locked, pos, pack_type, pack_index, exactpos, PANEL_OBJECT_DRAWER, id); if (!drawer->info) { @@ -624,7 +625,7 @@ panel_drawer_create (PanelToplevel *toplevel, char *id; id = panel_profile_prepare_object (PANEL_OBJECT_DRAWER, toplevel, position, - PANEL_OBJECT_PACK_START); + PANEL_OBJECT_PACK_START, 0); panel_drawer_prepare (id, custom_icon, use_custom_icon, tooltip, NULL); @@ -644,7 +645,7 @@ panel_drawer_create_with_id (const char *toplevel_id, char *attached_toplevel_id = NULL; id = panel_profile_prepare_object_with_id (PANEL_OBJECT_DRAWER, toplevel_id, position, - PANEL_OBJECT_PACK_START); + PANEL_OBJECT_PACK_START, 0); panel_drawer_prepare (id, custom_icon, use_custom_icon, tooltip, &attached_toplevel_id); @@ -660,6 +661,7 @@ drawer_load_from_gsettings (PanelWidget *panel_widget, gboolean locked, gint position, PanelObjectPackType pack_type, + int pack_index, const char *id) { gboolean use_custom_icon; @@ -694,6 +696,7 @@ drawer_load_from_gsettings (PanelWidget *panel_widget, locked, position, pack_type, + pack_index, TRUE, id); diff --git a/mate-panel/drawer.h b/mate-panel/drawer.h index b9c70a37..c48ac7b3 100644 --- a/mate-panel/drawer.h +++ b/mate-panel/drawer.h @@ -37,6 +37,7 @@ void drawer_load_from_gsettings (PanelWidget *panel_widget, gboolean locked, gint position, PanelObjectPackType pack_type, + int pack_index, const char *id); void panel_drawer_set_dnd_enabled (Drawer *drawer, diff --git a/mate-panel/launcher.c b/mate-panel/launcher.c index 4ec14f8b..54a824ac 100644 --- a/mate-panel/launcher.c +++ b/mate-panel/launcher.c @@ -881,6 +881,7 @@ load_launcher_applet (const char *location, gboolean locked, int pos, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id) { @@ -893,7 +894,7 @@ load_launcher_applet (const char *location, launcher->info = mate_panel_applet_register (launcher->button, launcher, free_launcher, - panel, locked, pos, pack_type, exactpos, + panel, locked, pos, pack_type, pack_index, exactpos, PANEL_OBJECT_LAUNCHER, id); if (!launcher->info) { free_launcher (launcher); @@ -919,6 +920,7 @@ launcher_load_from_gsettings (PanelWidget *panel_widget, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, const char *id) { GSettings *settings; @@ -947,6 +949,7 @@ launcher_load_from_gsettings (PanelWidget *panel_widget, locked, position, pack_type, + pack_index, TRUE, id); @@ -1097,7 +1100,7 @@ panel_launcher_create_with_id (const char *toplevel_id, id = panel_profile_prepare_object_with_id (PANEL_OBJECT_LAUNCHER, toplevel_id, position, - PANEL_OBJECT_PACK_START); + PANEL_OBJECT_PACK_START, 0); path = g_strdup_printf ("%s%s/", PANEL_OBJECT_PATH, id); settings = g_settings_new_with_path (PANEL_OBJECT_SCHEMA, path); diff --git a/mate-panel/launcher.h b/mate-panel/launcher.h index 37222cb3..a46b0a55 100644 --- a/mate-panel/launcher.h +++ b/mate-panel/launcher.h @@ -59,6 +59,7 @@ void launcher_load_from_gsettings (PanelWidget *panel_widget, gboolean locked, gint position, PanelObjectPackType pack_type, + int pack_index, const char *id); void panel_launcher_delete (Launcher *launcher); diff --git a/mate-panel/panel-action-button.c b/mate-panel/panel-action-button.c index e9ba8688..8135132b 100644 --- a/mate-panel/panel-action-button.c +++ b/mate-panel/panel-action-button.c @@ -899,6 +899,7 @@ panel_action_button_load (PanelActionButtonType type, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id) { @@ -911,7 +912,7 @@ panel_action_button_load (PanelActionButtonType type, button->priv->info = mate_panel_applet_register (GTK_WIDGET (button), NULL, NULL, panel, locked, position, - pack_type, exactpos, PANEL_OBJECT_ACTION, id); + pack_type, pack_index, exactpos, PANEL_OBJECT_ACTION, id); if (!button->priv->info) { gtk_widget_destroy (GTK_WIDGET (button)); return; @@ -945,7 +946,7 @@ panel_action_button_create (PanelToplevel *toplevel, char *path; id = panel_profile_prepare_object (PANEL_OBJECT_ACTION, toplevel, position, - PANEL_OBJECT_PACK_START); + PANEL_OBJECT_PACK_START, 0); path = g_strdup_printf (PANEL_OBJECT_PATH "%s/", id); settings = g_settings_new_with_path (PANEL_OBJECT_SCHEMA, path); @@ -966,6 +967,7 @@ panel_action_button_load_from_gsettings (PanelWidget *panel, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id) { @@ -982,7 +984,7 @@ panel_action_button_load_from_gsettings (PanelWidget *panel, g_object_unref (settings); panel_action_button_load (type, panel, locked, - position, pack_type, exactpos, id); + position, pack_type, pack_index, exactpos, id); } void diff --git a/mate-panel/panel-action-button.h b/mate-panel/panel-action-button.h index 713b333c..59805cc2 100644 --- a/mate-panel/panel-action-button.h +++ b/mate-panel/panel-action-button.h @@ -70,6 +70,7 @@ void panel_action_button_load_from_gsettings (PanelWidget *pan gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id); diff --git a/mate-panel/panel-applet-frame.c b/mate-panel/panel-applet-frame.c index fdeaada0..c1f20c3e 100644 --- a/mate-panel/panel-applet-frame.c +++ b/mate-panel/panel-applet-frame.c @@ -65,6 +65,7 @@ static void mate_panel_applet_frame_load (const gchar *iid, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id); @@ -73,6 +74,7 @@ struct _MatePanelAppletFrameActivating { PanelWidget *panel; int position; PanelObjectPackType pack_type; + int pack_index; gboolean exactpos; char *id; }; @@ -586,7 +588,8 @@ _mate_panel_applet_frame_activated (MatePanelAppletFrame *frame, info = mate_panel_applet_register (GTK_WIDGET (frame), GTK_WIDGET (frame), NULL, frame->priv->panel, frame_act->locked, frame_act->position, - frame_act->pack_type, frame_act->exactpos, + frame_act->pack_type, frame_act->pack_index, + frame_act->exactpos, PANEL_OBJECT_APPLET, frame_act->id); frame->priv->applet_info = info; @@ -719,8 +722,20 @@ mate_panel_applet_frame_reload_response (GtkWidget *dialog, mate_panel_applet_clean (info); } + AppletData *applet_data; + PanelObjectPackType pack_type = PANEL_OBJECT_PACK_START; + int pack_idx = 0; + + if (info) { + applet_data = g_object_get_data (G_OBJECT (info->widget), MATE_PANEL_APPLET_DATA); + if (applet_data) { + pack_type = applet_data->pack_type; + pack_idx = applet_data->pack_index; + } + } + mate_panel_applet_frame_load (iid, panel, locked, - position, PANEL_OBJECT_PACK_START, TRUE, id); + position, pack_type, pack_idx, TRUE, id); g_free (iid); g_free (id); @@ -1002,6 +1017,7 @@ mate_panel_applet_frame_load (const gchar *iid, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id) { @@ -1023,12 +1039,13 @@ mate_panel_applet_frame_load (const gchar *iid, } frame_act = g_slice_new0 (MatePanelAppletFrameActivating); - frame_act->locked = locked; - frame_act->panel = panel; - frame_act->position = position; - frame_act->pack_type = pack_type; - frame_act->exactpos = exactpos; - frame_act->id = g_strdup (id); + frame_act->locked = locked; + frame_act->panel = panel; + frame_act->position = position; + frame_act->pack_type = pack_type; + frame_act->pack_index = pack_index; + frame_act->exactpos = exactpos; + frame_act->id = g_strdup (id); if (!mate_panel_applets_manager_load_applet (iid, frame_act)) { mate_panel_applet_frame_loading_failed (iid, panel, id); @@ -1041,6 +1058,7 @@ mate_panel_applet_frame_load_from_gsettings (PanelWidget *panel_widget, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, const char *id) { GSettings *settings; @@ -1062,7 +1080,7 @@ mate_panel_applet_frame_load_from_gsettings (PanelWidget *panel_widget, } mate_panel_applet_frame_load (applet_iid, panel_widget, - locked, position, pack_type, TRUE, id); + locked, position, pack_type, pack_index, TRUE, id); g_free (applet_iid); } @@ -1079,7 +1097,7 @@ mate_panel_applet_frame_create (PanelToplevel *toplevel, g_return_if_fail (iid != NULL); id = panel_profile_prepare_object (PANEL_OBJECT_APPLET, toplevel, position, - PANEL_OBJECT_PACK_START); + PANEL_OBJECT_PACK_START, 0); path = g_strdup_printf (PANEL_OBJECT_PATH "%s/", id); settings = g_settings_new_with_path (PANEL_OBJECT_SCHEMA, path); diff --git a/mate-panel/panel-applet-frame.h b/mate-panel/panel-applet-frame.h index 05228895..18d6943f 100644 --- a/mate-panel/panel-applet-frame.h +++ b/mate-panel/panel-applet-frame.h @@ -87,6 +87,7 @@ void mate_panel_applet_frame_load_from_gsettings (PanelWidget *panel gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, const char *id); void mate_panel_applet_frame_sync_menu_state (MatePanelAppletFrame *frame); diff --git a/mate-panel/panel-layout.c b/mate-panel/panel-layout.c index 0846a7e7..c0ab9ba6 100644 --- a/mate-panel/panel-layout.c +++ b/mate-panel/panel-layout.c @@ -81,6 +81,7 @@ static PanelLayoutKeyDefinition panel_layout_object_keys[] = { { PANEL_OBJECT_TYPE_KEY, G_TYPE_STRING }, { PANEL_OBJECT_TOPLEVEL_ID_KEY, G_TYPE_STRING }, { PANEL_OBJECT_PACK_TYPE_KEY, G_TYPE_STRING }, + { PANEL_OBJECT_PACK_INDEX_KEY, G_TYPE_INT }, { PANEL_OBJECT_POSITION_KEY, G_TYPE_INT }, { PANEL_OBJECT_PANEL_RIGHT_STICK_KEY, G_TYPE_BOOLEAN }, { PANEL_OBJECT_LOCKED_KEY, G_TYPE_BOOLEAN }, diff --git a/mate-panel/panel-menu-bar.c b/mate-panel/panel-menu-bar.c index 7862bc40..1d9b6979 100644 --- a/mate-panel/panel-menu-bar.c +++ b/mate-panel/panel-menu-bar.c @@ -339,7 +339,7 @@ static gboolean panel_menu_bar_on_draw (GtkWidget* widget, cairo_t* cr, gpointer return FALSE; } -static void panel_menu_bar_load(PanelWidget* panel, gboolean locked, int position, PanelObjectPackType pack_type, gboolean exactpos, const char* id) +static void panel_menu_bar_load(PanelWidget* panel, gboolean locked, int position, PanelObjectPackType pack_type, int pack_index, gboolean exactpos, const char* id) { PanelMenuBar* menubar; GtkSettings* settings; @@ -348,7 +348,7 @@ static void panel_menu_bar_load(PanelWidget* panel, gboolean locked, int positio menubar = g_object_new(PANEL_TYPE_MENU_BAR, NULL); - menubar->priv->info = mate_panel_applet_register(GTK_WIDGET(menubar), NULL, NULL, panel, locked, position, pack_type, exactpos, PANEL_OBJECT_MENU_BAR, id); + menubar->priv->info = mate_panel_applet_register(GTK_WIDGET(menubar), NULL, NULL, panel, locked, position, pack_type, pack_index, exactpos, PANEL_OBJECT_MENU_BAR, id); if (!menubar->priv->info) { @@ -377,9 +377,9 @@ static void panel_menu_bar_load(PanelWidget* panel, gboolean locked, int positio panel_menu_bar_update_visibility(menubar->priv->settings, NULL, menubar); } -void panel_menu_bar_load_from_gsettings (PanelWidget* panel, gboolean locked, int position, PanelObjectPackType pack_type, gboolean exactpos, const char* id) +void panel_menu_bar_load_from_gsettings (PanelWidget* panel, gboolean locked, int position, PanelObjectPackType pack_type, int pack_index, gboolean exactpos, const char* id) { - panel_menu_bar_load(panel, locked, position, pack_type, exactpos, id); + panel_menu_bar_load(panel, locked, position, pack_type, pack_index, exactpos, id); } void panel_menu_bar_create(PanelToplevel* toplevel, int position) @@ -387,7 +387,7 @@ void panel_menu_bar_create(PanelToplevel* toplevel, int position) char* id; id = panel_profile_prepare_object(PANEL_OBJECT_MENU_BAR, toplevel, position, - PANEL_OBJECT_PACK_START); + PANEL_OBJECT_PACK_START, 0); panel_profile_add_to_list(PANEL_GSETTINGS_OBJECTS, id); g_free(id); } diff --git a/mate-panel/panel-menu-bar.h b/mate-panel/panel-menu-bar.h index 556bb432..4ac34199 100644 --- a/mate-panel/panel-menu-bar.h +++ b/mate-panel/panel-menu-bar.h @@ -63,6 +63,7 @@ void panel_menu_bar_load_from_gsettings (PanelWidget *panel, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id); diff --git a/mate-panel/panel-menu-button.c b/mate-panel/panel-menu-button.c index 5bb1e24f..c7e2fd31 100644 --- a/mate-panel/panel-menu-button.c +++ b/mate-panel/panel-menu-button.c @@ -669,6 +669,7 @@ panel_menu_button_load (const char *menu_path, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, gboolean has_arrow, const char *id) @@ -688,7 +689,7 @@ panel_menu_button_load (const char *menu_path, NULL); info = mate_panel_applet_register (GTK_WIDGET (button), NULL, NULL, - panel, locked, position, pack_type, exactpos, + panel, locked, position, pack_type, pack_index, exactpos, PANEL_OBJECT_MENU, id); if (!info) { gtk_widget_destroy (GTK_WIDGET (button)); @@ -917,6 +918,7 @@ panel_menu_button_load_from_gsettings (PanelWidget *panel, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id) { @@ -948,6 +950,7 @@ panel_menu_button_load_from_gsettings (PanelWidget *panel, locked, position, pack_type, + pack_index, exactpos, has_arrow, id); @@ -973,7 +976,7 @@ panel_menu_button_create (PanelToplevel *toplevel, char *id; id = panel_profile_prepare_object (PANEL_OBJECT_MENU, toplevel, position, - PANEL_OBJECT_PACK_START); + PANEL_OBJECT_PACK_START, 0); path = g_strdup_printf (PANEL_OBJECT_PATH "%s/", id); settings = g_settings_new_with_path (PANEL_OBJECT_SCHEMA, path); diff --git a/mate-panel/panel-menu-button.h b/mate-panel/panel-menu-button.h index a246b0df..f38a81e0 100644 --- a/mate-panel/panel-menu-button.h +++ b/mate-panel/panel-menu-button.h @@ -81,6 +81,7 @@ void panel_menu_button_load_from_gsettings (PanelWidget *panel, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, gboolean exactpos, const char *id); diff --git a/mate-panel/panel-profile.c b/mate-panel/panel-profile.c index 1c3ab97c..512a18b3 100644 --- a/mate-panel/panel-profile.c +++ b/mate-panel/panel-profile.c @@ -1251,7 +1251,8 @@ char * panel_profile_prepare_object_with_id (PanelObjectType object_type, const char *toplevel_id, int position, - PanelObjectPackType pack_type) + PanelObjectPackType pack_type, + int pack_index) { PanelGSettingsKeyType key_type; char *id; @@ -1269,6 +1270,7 @@ panel_profile_prepare_object_with_id (PanelObjectType object_type, g_settings_set_string (settings, PANEL_OBJECT_TOPLEVEL_ID_KEY, toplevel_id); g_settings_set_int (settings, PANEL_OBJECT_POSITION_KEY, position); g_settings_set_enum (settings, PANEL_OBJECT_PACK_TYPE_KEY, pack_type); + g_settings_set_int (settings, PANEL_OBJECT_PACK_INDEX_KEY, pack_index); /* Force writing the settings in order to reserve the object ID *now*, * so that a later call to panel_profile_find_new_id() won't find the same @@ -1285,12 +1287,14 @@ char * panel_profile_prepare_object (PanelObjectType object_type, PanelToplevel *toplevel, int position, - PanelObjectPackType pack_type) + PanelObjectPackType pack_type, + int pack_index) { return panel_profile_prepare_object_with_id (object_type, panel_profile_get_toplevel_id (toplevel), position, - pack_type); + pack_type, + pack_index); } void @@ -1313,6 +1317,7 @@ panel_profile_load_object (char *id) char *toplevel_id; int position; PanelObjectPackType pack_type; + int pack_index; gboolean right_stick; gboolean locked; GSettings *settings; @@ -1324,6 +1329,7 @@ panel_profile_load_object (char *id) position = g_settings_get_int (settings, PANEL_OBJECT_POSITION_KEY); toplevel_id = g_settings_get_string (settings, PANEL_OBJECT_TOPLEVEL_ID_KEY); pack_type = g_settings_get_enum (settings, PANEL_OBJECT_PACK_TYPE_KEY); + pack_index = g_settings_get_int (settings, PANEL_OBJECT_PACK_INDEX_KEY); right_stick = g_settings_get_boolean (settings, PANEL_OBJECT_PANEL_RIGHT_STICK_KEY); locked = g_settings_get_boolean (settings, PANEL_OBJECT_LOCKED_KEY); @@ -1338,6 +1344,7 @@ panel_profile_load_object (char *id) toplevel_id, position, pack_type, + pack_index, locked); g_free (toplevel_id); diff --git a/mate-panel/panel-profile.h b/mate-panel/panel-profile.h index 9f480a15..152603e2 100644 --- a/mate-panel/panel-profile.h +++ b/mate-panel/panel-profile.h @@ -62,11 +62,13 @@ void panel_profile_delete_toplevel (PanelToplevel *toplevel char *panel_profile_prepare_object (PanelObjectType object_type, PanelToplevel *toplevel, int position, - PanelObjectPackType pack_type); + PanelObjectPackType pack_type, + int pack_index); char *panel_profile_prepare_object_with_id (PanelObjectType object_type, const char *toplevel_id, int position, - PanelObjectPackType pack_type); + PanelObjectPackType pack_type, + int pack_index); void panel_profile_delete_object (AppletInfo *applet_info); gboolean panel_profile_key_is_writable (PanelToplevel *toplevel, diff --git a/mate-panel/panel-schemas.h b/mate-panel/panel-schemas.h index 15b6e9fb..6b22e2a7 100644 --- a/mate-panel/panel-schemas.h +++ b/mate-panel/panel-schemas.h @@ -46,6 +46,7 @@ #define PANEL_OBJECT_TYPE_KEY "object-type" #define PANEL_OBJECT_TOPLEVEL_ID_KEY "toplevel-id" #define PANEL_OBJECT_PACK_TYPE_KEY "pack-type" +#define PANEL_OBJECT_PACK_INDEX_KEY "pack-index" #define PANEL_OBJECT_POSITION_KEY "position" #define PANEL_OBJECT_PANEL_RIGHT_STICK_KEY "panel-right-stick" #define PANEL_OBJECT_LOCKED_KEY "locked" diff --git a/mate-panel/panel-separator.c b/mate-panel/panel-separator.c index e4ef14f0..a9544726 100644 --- a/mate-panel/panel-separator.c +++ b/mate-panel/panel-separator.c @@ -233,6 +233,7 @@ panel_separator_load_from_gsettings (PanelWidget *panel, gboolean locked, int position, PanelObjectPackType pack_type, + int pack_index, const char *id) { PanelSeparator *separator; @@ -242,7 +243,7 @@ panel_separator_load_from_gsettings (PanelWidget *panel, separator->priv->info = mate_panel_applet_register (GTK_WIDGET (separator), NULL, NULL, panel, locked, position, - pack_type, TRUE, + pack_type, pack_index, TRUE, PANEL_OBJECT_SEPARATOR, id); @@ -265,7 +266,7 @@ panel_separator_create (PanelToplevel *toplevel, id = panel_profile_prepare_object (PANEL_OBJECT_SEPARATOR, toplevel, - position, PANEL_OBJECT_PACK_START); + position, PANEL_OBJECT_PACK_START, 0); panel_profile_add_to_list (PANEL_GSETTINGS_OBJECTS, id); g_free (id); } diff --git a/mate-panel/panel-separator.h b/mate-panel/panel-separator.h index 6c1f363b..fe6827e9 100644 --- a/mate-panel/panel-separator.h +++ b/mate-panel/panel-separator.h @@ -61,6 +61,7 @@ void panel_separator_load_from_gsettings (PanelWidget *panel_widget, gboolean locked, gint position, PanelObjectPackType pack_type, + int pack_index, const char *id); void panel_separator_set_orientation (PanelSeparator *separator, PanelOrientation orientation); diff --git a/mate-panel/panel-widget.c b/mate-panel/panel-widget.c index 9f510e12..00ee37b1 100644 --- a/mate-panel/panel-widget.c +++ b/mate-panel/panel-widget.c @@ -88,6 +88,7 @@ static void panel_widget_switch_move_applet (PanelWidget *panel, GtkDirectionType dir); static void panel_widget_free_move_applet (PanelWidget *panel, GtkDirectionType dir); +static void panel_widget_update_positions (PanelWidget *panel); static void panel_widget_tab_move (PanelWidget *panel, gboolean next); static void panel_widget_end_move (PanelWidget *panel); @@ -107,6 +108,19 @@ static gboolean panel_widget_push_applet_left (PanelWidget *panel, static int applet_data_compare (AppletData *ad1, AppletData *ad2) { + if (ad1->pack_type != ad2->pack_type) + return ad1->pack_type - ad2->pack_type; /* start < center < end */ + + /* Within the same pack zone, sort by pack_index. For END zone, + * higher index = leftmost (closer to center), so reverse. */ + if (ad1->pack_index != ad2->pack_index) { + if (ad1->pack_type != PANEL_OBJECT_PACK_END) + return ad1->pack_index - ad2->pack_index; + else + return ad2->pack_index - ad1->pack_index; + } + + /* Fallback to pixel position in case all pack_index are 0. */ return ad1->pos - ad2->pos; } @@ -550,8 +564,8 @@ panel_widget_cadd (GtkContainer *container, g_return_if_fail (PANEL_IS_WIDGET (container)); g_return_if_fail (GTK_IS_WIDGET (widget)); - panel_widget_add (PANEL_WIDGET (container), widget, FALSE, - 0, PANEL_OBJECT_PACK_START, FALSE); + panel_widget_add (PANEL_WIDGET (container), widget, FALSE, 0, + PANEL_OBJECT_PACK_START, 0, FALSE); p = g_object_get_data (G_OBJECT(widget), MATE_PANEL_APPLET_ASSOC_PANEL_KEY); @@ -1193,6 +1207,194 @@ panel_widget_right_stick(PanelWidget *panel,int old_size) emit_applet_moved (panel, list->data); } +/* data should be freed with g_list_free() */ +static GList * +get_applet_list_pack (PanelWidget *panel, + PanelObjectPackType pack_type) +{ + GList *ret; + GList *l; + GList *prev; + + g_return_val_if_fail (PANEL_IS_WIDGET (panel), NULL); + + for (l = panel->applet_list; l; l = l->next) { + AppletData *ad = l->data; + + if (ad->pack_type == pack_type) + break; + } + + if (!l) + return NULL; + + ret = g_list_copy (l); + for (l = ret; l; l = l->next) { + AppletData *ad = l->data; + if (ad->pack_type != pack_type) + break; + } + + if (!l) + return ret; + + prev = l->prev; + if (prev) + prev->next = NULL; + g_list_free (l); + + return ret; +} + +/* Note: this can only be called at the beginning of size_allocate, which means + * that ad->constrained doesn't matter yet (it will be set to the correct + * value in size_allocate). */ +static void +panel_widget_update_positions_packed_start (PanelWidget *panel) +{ + GList *list,*l; + AppletData *ad; + int size_all = 0; + int pos_next; + + if (panel->packed) + return; + + list = get_applet_list_pack (panel, PANEL_OBJECT_PACK_START); + + /* get size used by the objects */ + for (l = list; l; l = l->next) { + ad = l->data; + size_all += ad->cells; + } + + /* update absolute position of all applets based on this information, + * starting with the first object */ + pos_next = 0; + l = list; + + while (l) { + ad = l->data; + ad->constrained = pos_next; + pos_next += ad->cells; + l = l->next; + } + + g_list_free (list); +} + +/* Note: only use this function when you can; see comment above + * panel_widget_update_positions_packed_start() */ +static void +panel_widget_update_positions_packed_end (PanelWidget *panel) +{ + GList *list,*l; + AppletData *ad; + int size_all = 0; + int pos_next; + + if (panel->packed) + return; + + list = get_applet_list_pack (panel, PANEL_OBJECT_PACK_END); + + /* get size used by the objects */ + for (l = list; l; l = l->next) { + ad = l->data; + size_all += ad->cells; + } + + /* update absolute position of all applets based on this information, + * starting with the first object */ + pos_next = panel->size - size_all; + l = list; + + while (l) { + ad = l->data; + ad->constrained = pos_next; + pos_next += ad->cells; + l = l->next; + } + + g_list_free (list); +} + +static void +panel_widget_update_positions (PanelWidget *panel) +{ + int i = 0; + GList *list; + AppletData *ad; + + i = 0; + + if (panel->packed) { + /* keep in sync with code in size_allocate */ + for (list = panel->applet_list; + list != NULL; + list = g_list_next (list)) { + ad = list->data; + ad->constrained = i; + i += ad->cells; + } + } else { + /* Re-compute the ideal position of objects, based on their size */ + panel_widget_update_positions_packed_start (panel); + panel_widget_update_positions_packed_end (panel); + + /* Second pass: try to position from the start, to make sure + * there's enough room. Also respect ad->pos for backward + * compat with configs not yet migrated to pack-type/pack-index. */ + for (list = panel->applet_list; + list != NULL; + list = g_list_next (list)) { + ad = list->data; + + /* Use the larger of zone position and old pixel + * position, so pre-migration gaps are preserved. */ + if (ad->pos > ad->constrained) + ad->constrained = ad->pos; + if (ad->constrained < i) + ad->constrained = i; + + i = ad->constrained + ad->cells; + } + + /* Third pass: try to push applets to the left to see if + * there is enough room. */ + if (i > panel->size) { + i = panel->size; + for (list = g_list_last (panel->applet_list); + list != NULL; + list = g_list_previous (list)) { + ad = list->data; + + if (ad->constrained + ad->cells > i) + ad->constrained = MAX (i - ad->cells, 0); + + i = ad->constrained; + } + } + + /* EEEEK, there's not enough room, so shift applets even + * at the expense of perhaps running out of room on the + * right if there is no free space in the middle */ + if (i < 0) { + i = 0; + for (list = panel->applet_list; + list != NULL; + list = g_list_next (list)) { + ad = list->data; + + if (ad->constrained < i) + ad->constrained = i; + + i = ad->constrained + ad->cells; + } + } + } +} + static void panel_widget_get_preferred_size(GtkWidget *widget, GtkRequisition *minimum_size, @@ -1362,7 +1564,6 @@ panel_widget_size_allocate(GtkWidget *widget, GtkAllocation *allocation) PanelWidget *panel; GList *list; int i; - int old_size; gboolean ltr; g_return_if_fail(PANEL_IS_WIDGET(widget)); @@ -1370,7 +1571,6 @@ panel_widget_size_allocate(GtkWidget *widget, GtkAllocation *allocation) panel = PANEL_WIDGET(widget); - old_size = panel->size; ltr = gtk_widget_get_direction (widget) == GTK_TEXT_DIR_LTR; gtk_widget_set_allocation (widget, allocation); @@ -1385,8 +1585,6 @@ panel_widget_size_allocate(GtkWidget *widget, GtkAllocation *allocation) panel->size = allocation->width; else panel->size = allocation->height; - if(old_size<panel->size) - panel_widget_right_stick(panel,old_size); if (panel->packed) { /* we're assuming the order is the same as the one that was @@ -1443,8 +1641,7 @@ panel_widget_size_allocate(GtkWidget *widget, GtkAllocation *allocation) } else { /*not packed*/ - /* First make sure there's enough room on the left */ - i = 0; + /* First pass: set ad->cells from applet sizes */ for (list = panel->applet_list; list != NULL; list = g_list_next (list)) { @@ -1463,15 +1660,12 @@ panel_widget_size_allocate(GtkWidget *widget, GtkAllocation *allocation) ad->cells = ad->size_hints [ad->size_hints_len - 1]; ad->min_cells = ad->size_hints [ad->size_hints_len - 1]; } - - ad->constrained = ad->pos; - if (ad->constrained < i) - ad->constrained = i; - - i = ad->constrained + ad->cells; } - /* Now expand from the right */ + /* Compute zone-based positions and resolve collisions */ + panel_widget_update_positions (panel); + + /* Now expand from the right, using size hints */ i = panel->size; for(list = g_list_last(panel->applet_list); list!=NULL; @@ -1495,23 +1689,6 @@ panel_widget_size_allocate(GtkWidget *widget, GtkAllocation *allocation) i = ad->constrained; } - /* EEEEK, there's not enough room, so shift applets even - * at the expense of perhaps running out of room on the - * right if there is no free space in the middle */ - if(i < 0) { - i = 0; - for(list = panel->applet_list; - list!=NULL; - list = g_list_next(list)) { - AppletData *ad = list->data; - - if (ad->constrained < i) - ad->constrained = i; - - i = ad->constrained + ad->cells; - } - } - for(list = panel->applet_list; list!=NULL; list = g_list_next(list)) { @@ -2449,6 +2626,7 @@ panel_widget_add (PanelWidget *panel, gboolean locked, int pos, PanelObjectPackType pack_type, + int pack_index, gboolean insert_at_pos) { AppletData *ad = NULL; @@ -2492,6 +2670,8 @@ panel_widget_add (PanelWidget *panel, if (ad == NULL) { ad = g_new (AppletData, 1); ad->applet = applet; + ad->pack_type = pack_type; + ad->pack_index = pack_index; ad->cells = 1; ad->min_cells = 1; ad->pos = pos; diff --git a/mate-panel/panel-widget.h b/mate-panel/panel-widget.h index c1c388dd..ed39b1f9 100644 --- a/mate-panel/panel-widget.h +++ b/mate-panel/panel-widget.h @@ -65,6 +65,8 @@ struct _AppletSizeHintsAlloc { struct _AppletData { GtkWidget * applet; + PanelObjectPackType pack_type; + int pack_index; int pos; int constrained; int cells; @@ -151,12 +153,13 @@ GtkWidget * panel_widget_new (PanelToplevel *toplevel, int sz); /*add an applet to the panel, preferably at position pos, if insert_at_pos is on, we REALLY want to insert at the pos given by pos*/ -int panel_widget_add (PanelWidget *panel, - GtkWidget *applet, - gboolean locked, - int pos, +int panel_widget_add (PanelWidget *panel, + GtkWidget *applet, + gboolean locked, + int pos, PanelObjectPackType pack_type, - gboolean insert_at_pos); + int pack_index, + gboolean insert_at_pos); /*needs to be called for drawers after add*/ void panel_widget_add_forbidden (PanelWidget *panel); |
