all repos — openbox @ 2f09e0ce388f63c341cb328d795766e2bd0dc24b

openbox fork - make it a bit more like ryudo

Merge branch 'backport' into work

Conflicts:

	openbox/actions/all.h
	openbox/actions/session.c
	openbox/client.c
	openbox/event.c
	openbox/grab.c
Dana Jansens danakj@orodu.net
commit

2f09e0ce388f63c341cb328d795766e2bd0dc24b

parent

84843c3f9842046e34366202f1a8f80ce8565f91

M Makefile.amMakefile.am

@@ -187,7 +187,6 @@ openbox/actions/iconify.c \

openbox/actions/if.c \ openbox/actions/kill.c \ openbox/actions/layer.c \ - openbox/actions/session.c \ openbox/actions/lower.c \ openbox/actions/maximize.c \ openbox/actions/move.c \
M openbox/actions/all.copenbox/actions/all.c

@@ -9,7 +9,6 @@ action_showdesktop_startup();

action_reconfigure_startup(); action_exit_startup(); action_restart_startup(); - action_session_startup(); action_cyclewindows_startup(); action_breakchroot_startup(); action_close_startup();
M openbox/actions/all.hopenbox/actions/all.h

@@ -10,7 +10,6 @@ void action_showdesktop_startup(void);

void action_reconfigure_startup(void); void action_exit_startup(void); void action_restart_startup(void); -void action_session_startup(void); void action_cyclewindows_startup(void); void action_breakchroot_startup(void); void action_close_startup(void);
M openbox/actions/exit.copenbox/actions/exit.c

@@ -1,6 +1,7 @@

#include "openbox/actions.h" #include "openbox/openbox.h" #include "openbox/prompt.h" +#include "openbox/session.h" #include "gettext.h" typedef struct {

@@ -13,6 +14,7 @@

void action_exit_startup(void) { actions_register("Exit", setup_func, NULL, run_func, NULL, NULL); + actions_register("SessionLogout", setup_func, NULL, run_func, NULL, NULL); } static gpointer setup_func(xmlNodePtr node)

@@ -29,10 +31,18 @@

return o; } +static void do_exit(void) +{ + if (session_connected()) + session_request_logout(FALSE); + else + ob_exit(0); +} + static gboolean prompt_cb(ObPrompt *p, gint result, gpointer data) { if (result) - ob_exit(0); + do_exit(); return TRUE; /* call the cleanup func */ }

@@ -53,13 +63,19 @@ { _("Cancel"), 0 },

{ _("Exit"), 1 } }; - p = prompt_new(_("Are you sure you want to exit Openbox?"), - _("Exit Openbox"), - answers, 2, 0, 0, prompt_cb, prompt_cleanup, NULL); + if (session_connected()) + p = prompt_new(_("Are you sure you want to log out?"), + _("Log Out"), + answers, 2, 0, 0, prompt_cb, prompt_cleanup, NULL); + else + p = prompt_new(_("Are you sure you want to exit Openbox?"), + _("Exit Openbox"), + answers, 2, 0, 0, prompt_cb, prompt_cleanup, NULL); + prompt_show(p, NULL, FALSE); } else - ob_exit(0); + do_exit(); return FALSE; }
M openbox/client.copenbox/client.c

@@ -105,6 +105,8 @@ ObStackingLayer layer);

static void client_call_notifies(ObClient *self, GSList *list); static void client_ping_event(ObClient *self, gboolean dead); static void client_prompt_kill(ObClient *self); +static gboolean client_can_steal_focus(ObClient *self, Time steal_time, + Time launch_time); void client_startup(gboolean reconfig) {

@@ -418,121 +420,14 @@

ob_debug_type(OB_DEBUG_FOCUS, "Going to try activate new window? %s", activate ? "yes" : "no"); if (activate) { - gboolean raise = FALSE; - gboolean relative_focused; - gboolean parent_focused; - - parent_focused = (focus_client != NULL && - client_search_focus_parent(self)); - relative_focused = (focus_client != NULL && - (client_search_focus_tree_full(self) != NULL || - client_search_focus_group_full(self) != NULL)); - - /* This is focus stealing prevention */ - ob_debug_type(OB_DEBUG_FOCUS, - "Want to focus new window 0x%x at time %u " - "launched at %u (last user interaction time %u)", - self->window, map_time, launch_time, - event_last_user_time); - ob_debug_type(OB_DEBUG_FOCUS, - "Current focus_client: %s", - (focus_client ? focus_client->title : "(none)")); - ob_debug_type(OB_DEBUG_FOCUS, - "parent focused: %d relative focused: %d", - parent_focused, relative_focused); - - if (menu_frame_visible || moveresize_in_progress) { - activate = FALSE; - raise = TRUE; - ob_debug_type(OB_DEBUG_FOCUS, - "Not focusing the window because the user is inside " - "an Openbox menu or is move/resizing a window and " - "we don't want to interrupt them"); - } - - /* if it's on another desktop */ - else if (!(self->desktop == screen_desktop || - self->desktop == DESKTOP_ALL) && - /* the timestamp is from before you changed desktops */ - launch_time && screen_desktop_user_time && - !event_time_after(launch_time, screen_desktop_user_time)) - { - activate = FALSE; - raise = TRUE; - ob_debug_type(OB_DEBUG_FOCUS, - "Not focusing the window because its on another " - "desktop"); - } - /* If something is focused... */ - else if (focus_client) { - /* If the user is working in another window right now, then don't - steal focus */ - if (!parent_focused && - event_last_user_time && launch_time && - event_time_after(event_last_user_time, launch_time) && - event_last_user_time != launch_time && - event_time_after(event_last_user_time, - map_time - OB_EVENT_USER_TIME_DELAY)) - { - activate = FALSE; - ob_debug_type(OB_DEBUG_FOCUS, - "Not focusing the window because the user is " - "working in another window that is not " - "its parent"); - } - /* If the new window is a transient (and its relatives aren't - focused) */ - else if (client_has_parent(self) && !relative_focused) { - activate = FALSE; - ob_debug_type(OB_DEBUG_FOCUS, - "Not focusing the window because it is a " - "transient, and its relatives aren't focused"); - } - /* Don't steal focus from globally active clients. - I stole this idea from KWin. It seems nice. - */ - else if (!(focus_client->can_focus || - focus_client->focus_notify)) - { - activate = FALSE; - ob_debug_type(OB_DEBUG_FOCUS, - "Not focusing the window because a globally " - "active client has focus"); - } - /* Don't move focus if it's not going to go to this window - anyway */ - else if (client_focus_target(self) != self) { - activate = FALSE; - raise = TRUE; - ob_debug_type(OB_DEBUG_FOCUS, - "Not focusing the window because another window " - "would get the focus anyway"); - } - /* Don't move focus if the window is not visible on the current - desktop and none of its relatives are focused */ - else if (!(self->desktop == screen_desktop || - self->desktop == DESKTOP_ALL) && - !relative_focused) - { - activate = FALSE; - raise = TRUE; - ob_debug_type(OB_DEBUG_FOCUS, - "Not focusing the window because it is on " - "another desktop and no relatives are focused "); - } - } + activate = client_can_steal_focus(self, map_time, launch_time); if (!activate) { - ob_debug_type(OB_DEBUG_FOCUS, - "Focus stealing prevention activated for %s at " - "time %u (last user interaction time %u)", - self->title, map_time, event_last_user_time); - /* if the client isn't focused, then hilite it so the user - knows it is there */ - client_hilite(self, TRUE); - /* we may want to raise it even tho we're not activating it */ - if (raise && !client_restore_session_stacking(self)) - stacking_raise(CLIENT_AS_WINDOW(self)); + /* if the client isn't stealing focus, then hilite it so the user + knows it is there, but don't do this if we're restoring from a + session */ + if (!client_restore_session_stacking(self)) + client_hilite(self, TRUE); } } else {

@@ -781,6 +676,105 @@ frame_free(self->frame);

g_free(self); } +static gboolean client_can_steal_focus(ObClient *self, Time steal_time, + Time launch_time) +{ + gboolean steal; + gboolean relative_focused; + gboolean parent_focused; + + steal = TRUE; + + parent_focused = (focus_client != NULL && + client_search_focus_parent(self)); + relative_focused = (focus_client != NULL && + (client_search_focus_tree_full(self) != NULL || + client_search_focus_group_full(self) != NULL)); + + /* This is focus stealing prevention */ + ob_debug_type(OB_DEBUG_FOCUS, + "Want to focus new window 0x%x at time %u " + "launched at %u (last user interaction time %u)", + self->window, steal_time, launch_time, + event_last_user_time); + + /* if it's on another desktop */ + if (!(self->desktop == screen_desktop || + self->desktop == DESKTOP_ALL) && + /* the timestamp is from before you changed desktops */ + launch_time && screen_desktop_user_time && + !event_time_after(launch_time, screen_desktop_user_time)) + { + steal = FALSE; + ob_debug_type(OB_DEBUG_FOCUS, + "Not focusing the window because its on another " + "desktop\n"); + } + /* If something is focused... */ + else if (focus_client) { + /* If the user is working in another window right now, then don't + steal focus */ + if (!parent_focused && + event_last_user_time && launch_time && + event_time_after(event_last_user_time, launch_time) && + event_last_user_time != launch_time && + event_time_after(event_last_user_time, + steal_time - OB_EVENT_USER_TIME_DELAY)) + { + steal = FALSE; + ob_debug_type(OB_DEBUG_FOCUS, + "Not focusing the window because the user is " + "working in another window that is not " + "its parent"); + } + /* If the new window is a transient (and its relatives aren't + focused) */ + else if (client_has_parent(self) && !relative_focused) { + steal = FALSE; + ob_debug_type(OB_DEBUG_FOCUS, + "Not focusing the window because it is a " + "transient, and its relatives aren't focused"); + } + /* Don't steal focus from globally active clients. + I stole this idea from KWin. It seems nice. + */ + else if (!(focus_client->can_focus || + focus_client->focus_notify)) + { + steal = FALSE; + ob_debug_type(OB_DEBUG_FOCUS, + "Not focusing the window because a globally " + "active client has focus"); + } + /* Don't move focus if it's not going to go to this window + anyway */ + else if (client_focus_target(self) != self) { + steal = FALSE; + ob_debug_type(OB_DEBUG_FOCUS, + "Not focusing the window because another window " + "would get the focus anyway"); + } + /* Don't move focus if the window is not visible on the current + desktop and none of its relatives are focused */ + else if (!(self->desktop == screen_desktop || + self->desktop == DESKTOP_ALL) && + !relative_focused) + { + steal = FALSE; + ob_debug_type(OB_DEBUG_FOCUS, + "Not focusing the window because it is on " + "another desktop and no relatives are focused "); + } + } + + if (!steal) + ob_debug_type(OB_DEBUG_FOCUS, + "Focus stealing prevention activated for %s at " + "time %u (last user interaction time %u)", + self->title, steal_time, event_last_user_time); + return steal; +} + /*! Returns a new structure containing the per-app settings for this client. The returned structure needs to be freed with g_free. */ static ObAppSettings *client_get_settings_state(ObClient *self)

@@ -2550,10 +2544,6 @@ {

gboolean hide = FALSE; if (!client_should_show(self)) { - if (self == focus_client) { - event_cancel_all_key_grabs(); - } - /* We don't need to ignore enter events here. The window can hide/iconify in 3 different ways: 1 - through an x message. in this case we ignore all enter events

@@ -3443,8 +3433,18 @@

/* don't allow focused windows to hilite */ self->demands_attention = hilite && !client_focused(self); if (self->frame != NULL) { /* if we're mapping, just set the state */ - if (self->demands_attention) + if (self->demands_attention) { frame_flash_start(self->frame); + + /* if the window is on another desktop then raise it and make it + the most recently used window */ + if (self->desktop != screen_desktop && + self->desktop != DESKTOP_ALL) + { + stacking_raise(CLIENT_AS_WINDOW(self)); + focus_order_to_top(self); + } + } else frame_flash_stop(self->frame); client_change_state(self);

@@ -3759,8 +3759,6 @@ /* if using focus_delay, stop the timer now so that focus doesn't

go moving on us */ event_halt_focus_delay(); - event_cancel_all_key_grabs(); - obt_display_ignore_errors(TRUE); if (self->can_focus) {

@@ -3819,12 +3817,16 @@ client_focus(self);

} /* this function exists to map to the net_active_window message in the ewmh */ -void client_activate(ObClient *self, gboolean here, gboolean raise, +void client_activate(ObClient *self, gboolean desktop, gboolean raise, gboolean unshade, gboolean user) { - if (user || (self->desktop == DESKTOP_ALL || - self->desktop == screen_desktop)) - client_present(self, here, raise, unshade); + if ((user && (desktop || + self->desktop == DESKTOP_ALL || + self->desktop == screen_desktop)) || + client_can_steal_focus(self, event_curtime, CurrentTime)) + { + client_present(self, FALSE, raise, unshade); + } else client_hilite(self, TRUE); }
M openbox/client.hopenbox/client.h

@@ -573,14 +573,14 @@ gboolean client_focus(ObClient *self);

/*! Activates the client for use, focusing, uniconifying it, etc. To be used when the user deliberately selects a window for use. - @param here If true, then the client is brought to the current desktop; - otherwise, the desktop is changed to where the client lives. + @param desktop If true, and the window is on another desktop, it will still + be activated. @param raise If true, the client is brought to the front. @param unshade If true, the client is unshaded (if it is shaded) @param user If true, then a user action is what requested the activation; otherwise, it means an application requested it on its own */ -void client_activate(ObClient *self, gboolean here, gboolean raise, +void client_activate(ObClient *self, gboolean desktop, gboolean raise, gboolean unshade, gboolean user); /*! Bring all of its helper windows to its desktop. These are the utility and
M openbox/client_list_combined_menu.copenbox/client_list_combined_menu.c

@@ -114,7 +114,7 @@ }

else { ObClient *t = self->data.normal.data; if (t) { /* it's set to NULL if its destroyed */ - client_activate(t, FALSE, TRUE, TRUE, TRUE); + client_activate(t, TRUE, TRUE, TRUE, TRUE); /* if the window is omnipresent then we need to go to its desktop */ if (t->desktop == DESKTOP_ALL)
M openbox/client_list_menu.copenbox/client_list_menu.c

@@ -101,7 +101,7 @@ ObClient *c, guint state, gpointer data)

{ ObClient *t = self->data.normal.data; if (t) { /* it's set to NULL if its destroyed */ - client_activate(t, FALSE, TRUE, TRUE, TRUE); + client_activate(t, TRUE, TRUE, TRUE, TRUE); /* if the window is omnipresent then we need to go to its desktop */ if (t->desktop == DESKTOP_ALL)
M openbox/event.copenbox/event.c

@@ -1329,10 +1329,7 @@ (e->xclient.data.l[0] == 1 ? "application" :

(e->xclient.data.l[0] == 2 ? "user" : "INVALID")))); /* XXX make use of data.l[2] !? */ if (e->xclient.data.l[0] == 1 || e->xclient.data.l[0] == 2) { - /* don't use the user's timestamp for client_focus, cuz if it's - an old broken timestamp (happens all the time) then focus - won't move even though we're trying to move it - event_curtime = e->xclient.data.l[1];*/ + event_curtime = e->xclient.data.l[1]; if (e->xclient.data.l[1] == 0) ob_debug_type(OB_DEBUG_APP_BUGS, "_NET_ACTIVE_WINDOW message for window %s is"

@@ -1341,7 +1338,7 @@ } else

ob_debug_type(OB_DEBUG_APP_BUGS, "_NET_ACTIVE_WINDOW message for window %s is " "missing source indication", client->title); - client_activate(client, TRUE, TRUE, TRUE, + client_activate(client, FALSE, TRUE, TRUE, (e->xclient.data.l[0] == 0 || e->xclient.data.l[0] == 2)); } else if (msgtype == OBT_PROP_ATOM(NET_WM_MOVERESIZE)) {
M openbox/focus.copenbox/focus.c

@@ -83,10 +83,6 @@ /* uninstall the old colormap, and install the new one */

screen_install_colormap(focus_client, FALSE); screen_install_colormap(client, TRUE); - /* in the middle of cycling..? kill it. */ - focus_cycle_stop(focus_client); - focus_cycle_stop(client); - focus_client = client; if (client != NULL) {

@@ -195,8 +191,6 @@ }

/* nothing is focused, update the colormap and _the root property_ */ focus_set_client(NULL); - - event_cancel_all_key_grabs(); /* when nothing will be focused, send focus to the backup target */ XSetInputFocus(obt_display, screen_support_win, RevertToPointerRoot,
M openbox/session.copenbox/session.c

@@ -34,6 +34,7 @@ void session_startup(gint argc, gchar **argv) {}

void session_shutdown(gboolean permanent) {} GList* session_state_find(struct _ObClient *c) { return NULL; } void session_request_logout(gboolean silent) {} +gboolean session_connected(void) { return FALSE; } #else #include "debug.h"

@@ -157,6 +158,11 @@ session_saved_state = g_list_delete_link(session_saved_state,

session_saved_state); } } +} + +gboolean session_connected(void) +{ + return !!sm_conn; } /*! Connect to the session manager and set up our callback functions */
M openbox/session.hopenbox/session.h

@@ -55,4 +55,6 @@ GList* session_state_find(struct _ObClient *c);

void session_request_logout(gboolean silent); +gboolean session_connected(void); + #endif