summaryrefslogtreecommitdiff
path: root/openbox/client.c
diff options
context:
space:
mode:
authorDana Jansens <danakj@orodu.net>2010-10-14 19:40:41 -0400
committerDana Jansens <danakj@orodu.net>2011-01-24 14:19:22 -0500
commit95535e86237e6c89935eb7563f37f13474c466f2 (patch)
tree0c319165f6706e330ad8a23d407aa57410fe8c96 /openbox/client.c
parent76ae19924d79326892f0b851db740d7207e4e158 (diff)
Big changes to placement across multiple monitors.
Add a Primary option for which monitor to place new windows on. Make "Active" the default instead of "Any", which is just totally crazy. When a window is being placed in the FOREGROUND, use a monitor chosen in the following order: 1. same monitor as parent 2. primary monitor if placement=PRIMARY active monitor if placement=ACTIVE pointer monitor if placement=MOUSE 3. primary monitor 4. other monitors where the window has group members on the same desktop 5. other monitors where the window has group members on other desktops 6. other monitors When a window is being placed in the BACKGROUND, use a monitor chosen in the following order: 1. same monitor as parent 2. other monitors where the window has group members on the same desktop 2a. primary monitor in this set 2b. other monitors in this set 3. other monitors where the window has group members on other desktops 3a. primary monitor in this set 3b. other monitors in this set 4. other monitors 4a. primary monitor in this set 4b. other monitors in this set Decide to focus the new window before placing it, so we know if it will be placed in the foreground or background. Always choose a single monitor, then place on it, rather than possibly moving to a "backup" monitor. Unpredictable monitor placement is horrible.
Diffstat (limited to 'openbox/client.c')
-rw-r--r--openbox/client.c117
1 files changed, 55 insertions, 62 deletions
diff --git a/openbox/client.c b/openbox/client.c
index 8eeb052b..bdfe9391 100644
--- a/openbox/client.c
+++ b/openbox/client.c
@@ -192,7 +192,8 @@ void client_manage(Window window, ObPrompt *prompt)
{
ObClient *self;
XSetWindowAttributes attrib_set;
- gboolean activate = FALSE;
+ gboolean try_activate = FALSE;
+ gboolean do_activate;
ObAppSettings *settings;
gboolean transient = FALSE;
Rect place;
@@ -284,7 +285,7 @@ void client_manage(Window window, ObPrompt *prompt)
FALSE, FALSE, TRUE, TRUE, FALSE, FALSE,
settings->focus == 1))
{
- activate = TRUE;
+ try_activate = TRUE;
}
/* remove the client's border */
@@ -298,6 +299,14 @@ void client_manage(Window window, ObPrompt *prompt)
/* where the frame was placed is where the window was originally */
place = self->area;
+ ob_debug("Going to try activate new window? %s",
+ try_activate ? "yes" : "no");
+ if (try_activate)
+ do_activate = client_can_steal_focus(self, settings->focus,
+ event_time(), launch_time);
+ else
+ do_activate = FALSE;
+
/* figure out placement for the window if the window is new */
if (ob_state() == OB_STATE_RUNNING) {
ob_debug("Positioned: %s @ %d %d",
@@ -316,7 +325,8 @@ void client_manage(Window window, ObPrompt *prompt)
"program + user specified" :
"BADNESS !?")))), place.width, place.height);
- obplaced = place_client(self, &place.x, &place.y, settings);
+ obplaced = place_client(self, do_activate, &place.x, &place.y,
+ settings);
/* watch for buggy apps that ask to be placed at (0,0) when there is
a strut there */
@@ -424,13 +434,30 @@ void client_manage(Window window, ObPrompt *prompt)
client_apply_startup_state(self, place.x, place.y,
place.width, place.height);
- ob_debug_type(OB_DEBUG_FOCUS, "Going to try activate new window? %s",
- activate ? "yes" : "no");
- if (activate) {
- activate = client_can_steal_focus(self, settings->focus,
- event_time(), launch_time);
+ /* grab mouse bindings before showing the window */
+ mouse_grab_for_client(self, TRUE);
+
+ /* this has to happen before we try focus the window, but we want it to
+ happen after the client's stacking has been determined or it looks bad
+ */
+ {
+ gulong ignore_start;
+ if (!config_focus_under_mouse)
+ ignore_start = event_start_ignore_all_enters();
+
+ client_show(self);
+
+ if (!config_focus_under_mouse)
+ event_end_ignore_all_enters(ignore_start);
+ }
- if (!activate) {
+ /* activate/hilight/raise the window */
+ if (try_activate) {
+ if (do_activate) {
+ gboolean stacked = client_restore_session_stacking(self);
+ client_present(self, FALSE, !stacked, TRUE);
+ }
+ else {
/* 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 */
@@ -450,27 +477,6 @@ void client_manage(Window window, ObPrompt *prompt)
stacking_raise(CLIENT_AS_WINDOW(self));
}
- mouse_grab_for_client(self, TRUE);
-
- /* this has to happen before we try focus the window, but we want it to
- happen after the client's stacking has been determined or it looks bad
- */
- {
- gulong ignore_start;
- if (!config_focus_under_mouse)
- ignore_start = event_start_ignore_all_enters();
-
- client_show(self);
-
- if (!config_focus_under_mouse)
- event_end_ignore_all_enters(ignore_start);
- }
-
- if (activate) {
- gboolean stacked = client_restore_session_stacking(self);
- client_present(self, FALSE, !stacked, TRUE);
- }
-
/* add to client list/map */
client_list = g_list_append(client_list, self);
window_add(&self->window, CLIENT_AS_WINDOW(self));
@@ -693,22 +699,18 @@ static gboolean client_can_steal_focus(ObClient *self,
{
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 window 0x%x at time %u "
- "launched at %u (last user interaction time %u)",
- self->window, steal_time, launch_time,
- event_last_user_time);
+ ob_debug("Want to focus 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 ||
@@ -721,15 +723,13 @@ static gboolean client_can_steal_focus(ObClient *self,
!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");
+ ob_debug("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 &&
+ if (!relative_focused &&
event_last_user_time &&
(!launch_time ||
(event_time_after(event_last_user_time, launch_time) &&
@@ -738,18 +738,15 @@ static gboolean client_can_steal_focus(ObClient *self,
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");
+ ob_debug("Not focusing the window because the user is "
+ "working in another window that is not its relative");
}
/* 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");
+ ob_debug("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.
@@ -758,17 +755,15 @@ static gboolean client_can_steal_focus(ObClient *self,
focus_client->focus_notify))
{
steal = FALSE;
- ob_debug_type(OB_DEBUG_FOCUS,
- "Not focusing the window because a globally "
- "active client has focus");
+ ob_debug("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");
+ ob_debug("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 */
@@ -777,17 +772,15 @@ static gboolean client_can_steal_focus(ObClient *self,
!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 ");
+ ob_debug("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);
+ ob_debug("Focus stealing prevention activated for %s at "
+ "time %u (last user interaction time %u)",
+ self->title, steal_time, event_last_user_time);
return steal;
}