mirror of
https://github.com/brl/mutter.git
synced 2024-11-25 01:20:42 -05:00
Don't unconditionally place splashscreens (and other not-to-befocused
2005-02-12 Elijah Newren <newren@gmail.com> Don't unconditionally place splashscreens (and other not-to-befocused windows) below the focus window. Fixes #167042. * src/window.c: (intervening_user_event_occurred): new function taken from the timestamp comparison portion of the old window_takes_focus_on_map function, (window_state_on_map): new function with remainder of old window_takes_focus_on_map function that determines both whether the window will take focus and whether it should be placed on top, (meta_window_show): use place_on_top_on_map to determine window stacking instead of trying to infer it from takes_focus_on_map
This commit is contained in:
parent
d31a0829be
commit
9fa5c1d4b9
14
ChangeLog
14
ChangeLog
@ -1,3 +1,17 @@
|
|||||||
|
2005-02-12 Elijah Newren <newren@gmail.com>
|
||||||
|
|
||||||
|
Don't unconditionally place splashscreens (and other
|
||||||
|
not-to-befocused windows) below the focus window. Fixes #167042.
|
||||||
|
|
||||||
|
* src/window.c: (intervening_user_event_occurred): new function
|
||||||
|
taken from the timestamp comparison portion of the old
|
||||||
|
window_takes_focus_on_map function, (window_state_on_map): new
|
||||||
|
function with remainder of old window_takes_focus_on_map function
|
||||||
|
that determines both whether the window will take focus and
|
||||||
|
whether it should be placed on top, (meta_window_show): use
|
||||||
|
place_on_top_on_map to determine window stacking instead of trying
|
||||||
|
to infer it from takes_focus_on_map
|
||||||
|
|
||||||
2005-02-11 Elijah Newren <newren@gmail.com>
|
2005-02-11 Elijah Newren <newren@gmail.com>
|
||||||
|
|
||||||
Avoid new windows being obscured by the focus window (and thus
|
Avoid new windows being obscured by the focus window (and thus
|
||||||
|
206
src/window.c
206
src/window.c
@ -1542,104 +1542,134 @@ meta_window_queue_calc_showing (MetaWindow *window)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
window_takes_focus_on_map (MetaWindow *window)
|
intervening_user_event_occurred (MetaWindow *window)
|
||||||
{
|
{
|
||||||
Time compare;
|
Time compare;
|
||||||
|
MetaWindow *focus_window;
|
||||||
|
|
||||||
|
focus_window = window->display->focus_window;
|
||||||
|
|
||||||
|
meta_topic (META_DEBUG_STARTUP,
|
||||||
|
"COMPARISON:\n"
|
||||||
|
" net_wm_user_time_set : %d\n"
|
||||||
|
" net_wm_user_time : %lu\n"
|
||||||
|
" initial_timestamp_set: %d\n"
|
||||||
|
" initial_timestamp : %lu\n",
|
||||||
|
window->net_wm_user_time_set,
|
||||||
|
window->net_wm_user_time,
|
||||||
|
window->initial_timestamp_set,
|
||||||
|
window->initial_timestamp);
|
||||||
|
if (focus_window != NULL)
|
||||||
|
{
|
||||||
|
meta_topic (META_DEBUG_STARTUP,
|
||||||
|
"COMPARISON (continued):\n"
|
||||||
|
" focus_window : %s\n"
|
||||||
|
" fw->net_wm_user_time : %lu\n",
|
||||||
|
focus_window->desc,
|
||||||
|
focus_window->net_wm_user_time);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* We expect the most common case for not focusing a new window
|
||||||
|
* to be when a hint to not focus it has been set. Since we can
|
||||||
|
* deal with that case rapidly, we use special case it--this is
|
||||||
|
* merely a preliminary optimization. :)
|
||||||
|
*/
|
||||||
|
if ( ((window->net_wm_user_time_set == TRUE) &&
|
||||||
|
(window->net_wm_user_time == 0))
|
||||||
|
||
|
||||||
|
((window->initial_timestamp_set == TRUE) &&
|
||||||
|
(window->initial_timestamp == 0)))
|
||||||
|
{
|
||||||
|
meta_topic (META_DEBUG_STARTUP,
|
||||||
|
"window %s explicitly requested no focus\n",
|
||||||
|
window->desc);
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(window->net_wm_user_time_set) && !(window->initial_timestamp_set))
|
||||||
|
{
|
||||||
|
meta_topic (META_DEBUG_STARTUP,
|
||||||
|
"no information about window %s found\n",
|
||||||
|
window->desc);
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* To determine the "launch" time of an application,
|
||||||
|
* startup-notification can set the TIMESTAMP and the
|
||||||
|
* application (usually via its toolkit such as gtk or qt) can
|
||||||
|
* set the _NET_WM_USER_TIME. If both are set, then it means
|
||||||
|
* the user has interacted with the application since it
|
||||||
|
* launched, and _NET_WM_USER_TIME is the value that should be
|
||||||
|
* used in the comparison.
|
||||||
|
*/
|
||||||
|
compare = window->initial_timestamp_set ? window->initial_timestamp : 0;
|
||||||
|
compare = window->net_wm_user_time_set ? window->net_wm_user_time : compare;
|
||||||
|
|
||||||
|
if ((focus_window != NULL) &&
|
||||||
|
XSERVER_TIME_IS_BEFORE (compare, focus_window->net_wm_user_time))
|
||||||
|
{
|
||||||
|
meta_topic (META_DEBUG_STARTUP,
|
||||||
|
"window %s focus prevented by other activity; %lu < %lu\n",
|
||||||
|
window->desc, compare,
|
||||||
|
focus_window->net_wm_user_time);
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
meta_topic (META_DEBUG_STARTUP,
|
||||||
|
"new window %s with no intervening events\n",
|
||||||
|
window->desc);
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This function determines what state the window should have assuming that it
|
||||||
|
* and the focus_window have no relation
|
||||||
|
*/
|
||||||
|
static void
|
||||||
|
window_state_on_map (MetaWindow *window,
|
||||||
|
gboolean *takes_focus,
|
||||||
|
gboolean *places_on_top)
|
||||||
|
{
|
||||||
|
gboolean intervening_events;
|
||||||
|
|
||||||
|
intervening_events = intervening_user_event_occurred (window);
|
||||||
|
|
||||||
|
*takes_focus = !intervening_events;
|
||||||
|
*places_on_top = *takes_focus;
|
||||||
|
|
||||||
/* don't initially focus windows that are intended to not accept
|
/* don't initially focus windows that are intended to not accept
|
||||||
* focus
|
* focus
|
||||||
*/
|
*/
|
||||||
if (!(window->input || window->take_focus))
|
if (!(window->input || window->take_focus))
|
||||||
return FALSE;
|
{
|
||||||
|
*takes_focus = FALSE;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
switch (window->type)
|
switch (window->type)
|
||||||
{
|
{
|
||||||
|
case META_WINDOW_UTILITY:
|
||||||
|
case META_WINDOW_TOOLBAR:
|
||||||
|
*takes_focus = FALSE;
|
||||||
|
*places_on_top = FALSE;
|
||||||
|
break;
|
||||||
case META_WINDOW_DOCK:
|
case META_WINDOW_DOCK:
|
||||||
case META_WINDOW_DESKTOP:
|
case META_WINDOW_DESKTOP:
|
||||||
case META_WINDOW_UTILITY:
|
|
||||||
case META_WINDOW_SPLASHSCREEN:
|
case META_WINDOW_SPLASHSCREEN:
|
||||||
case META_WINDOW_TOOLBAR:
|
|
||||||
case META_WINDOW_MENU:
|
case META_WINDOW_MENU:
|
||||||
/* don't focus these */
|
/* don't focus any of these; places_on_top may be irrelevant for some of
|
||||||
|
* these (e.g. dock)--but you never know--the focus window might also be
|
||||||
|
* of the same type in some weird situation...
|
||||||
|
*/
|
||||||
|
*takes_focus = FALSE;
|
||||||
break;
|
break;
|
||||||
case META_WINDOW_NORMAL:
|
case META_WINDOW_NORMAL:
|
||||||
case META_WINDOW_DIALOG:
|
case META_WINDOW_DIALOG:
|
||||||
case META_WINDOW_MODAL_DIALOG:
|
case META_WINDOW_MODAL_DIALOG:
|
||||||
meta_topic (META_DEBUG_STARTUP,
|
/* The default is correct for these */
|
||||||
"COMPARISON:\n"
|
|
||||||
" net_wm_user_time_set : %d\n"
|
|
||||||
" net_wm_user_time : %lu\n"
|
|
||||||
" initial_timestamp_set: %d\n"
|
|
||||||
" initial_timestamp : %lu\n",
|
|
||||||
window->net_wm_user_time_set,
|
|
||||||
window->net_wm_user_time,
|
|
||||||
window->initial_timestamp_set,
|
|
||||||
window->initial_timestamp);
|
|
||||||
if (window->display->focus_window != NULL) {
|
|
||||||
meta_topic (META_DEBUG_STARTUP,
|
|
||||||
"COMPARISON (continued):\n"
|
|
||||||
" focus_window : %s\n"
|
|
||||||
" fw->net_wm_user_time : %lu\n",
|
|
||||||
window->display->focus_window->desc,
|
|
||||||
window->display->focus_window->net_wm_user_time);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* We expect the most common case for not focusing a new window
|
|
||||||
* to be when a hint to not focus it has been set. Since we can
|
|
||||||
* deal with that case rapidly, we use special case it--this is
|
|
||||||
* merely a preliminary optimization. :)
|
|
||||||
*/
|
|
||||||
if ( ((window->net_wm_user_time_set == TRUE) &&
|
|
||||||
(window->net_wm_user_time == 0))
|
|
||||||
||
|
|
||||||
((window->initial_timestamp_set == TRUE) &&
|
|
||||||
(window->initial_timestamp == 0)))
|
|
||||||
{
|
|
||||||
meta_topic (META_DEBUG_STARTUP,
|
|
||||||
"window %s explicitly requested no focus\n",
|
|
||||||
window->desc);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!(window->net_wm_user_time_set) && !(window->initial_timestamp_set))
|
|
||||||
{
|
|
||||||
meta_topic (META_DEBUG_STARTUP,
|
|
||||||
"no information about window %s found\n",
|
|
||||||
window->desc);
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* To determine the "launch" time of an application,
|
|
||||||
* startup-notification can set the TIMESTAMP and the
|
|
||||||
* application (usually via its toolkit such as gtk or qt) can
|
|
||||||
* set the _NET_WM_USER_TIME. If both are set, then it means
|
|
||||||
* the user has interacted with the application since it
|
|
||||||
* launched, and _NET_WM_USER_TIME is the value that should be
|
|
||||||
* used in the comparison.
|
|
||||||
*/
|
|
||||||
compare = window->initial_timestamp_set ? window->initial_timestamp : 0;
|
|
||||||
compare = window->net_wm_user_time_set ? window->net_wm_user_time : compare;
|
|
||||||
|
|
||||||
if ((window->display->focus_window != NULL) &&
|
|
||||||
XSERVER_TIME_IS_BEFORE (compare, window->display->focus_window->net_wm_user_time))
|
|
||||||
{
|
|
||||||
meta_topic (META_DEBUG_STARTUP,
|
|
||||||
"window %s focus prevented by other activity; %lu is before %lu\n",
|
|
||||||
window->desc, compare, window->display->focus_window->net_wm_user_time);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
meta_topic (META_DEBUG_STARTUP,
|
|
||||||
"new window %s with no intervening events\n",
|
|
||||||
window->desc);
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return FALSE;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -1648,6 +1678,7 @@ meta_window_show (MetaWindow *window)
|
|||||||
gboolean did_placement;
|
gboolean did_placement;
|
||||||
gboolean did_show;
|
gboolean did_show;
|
||||||
gboolean takes_focus_on_map;
|
gboolean takes_focus_on_map;
|
||||||
|
gboolean place_on_top_on_map;
|
||||||
|
|
||||||
meta_topic (META_DEBUG_WINDOW_STATE,
|
meta_topic (META_DEBUG_WINDOW_STATE,
|
||||||
"Showing window %s, shaded: %d iconic: %d placed: %d\n",
|
"Showing window %s, shaded: %d iconic: %d placed: %d\n",
|
||||||
@ -1655,11 +1686,18 @@ meta_window_show (MetaWindow *window)
|
|||||||
|
|
||||||
did_show = FALSE;
|
did_show = FALSE;
|
||||||
did_placement = FALSE;
|
did_placement = FALSE;
|
||||||
takes_focus_on_map = window_takes_focus_on_map (window);
|
window_state_on_map (window, &takes_focus_on_map, &place_on_top_on_map);
|
||||||
|
|
||||||
if ( (!takes_focus_on_map) && (window->display->focus_window != NULL) )
|
meta_topic (META_DEBUG_WINDOW_STATE,
|
||||||
|
"Window %s %s focus on map, and %s place on top on map.\n",
|
||||||
|
window->desc,
|
||||||
|
takes_focus_on_map ? "does" : "does not",
|
||||||
|
place_on_top_on_map ? "does" : "does not");
|
||||||
|
|
||||||
|
if ( !takes_focus_on_map &&
|
||||||
|
window->display->focus_window != NULL &&
|
||||||
|
!place_on_top_on_map )
|
||||||
{
|
{
|
||||||
|
|
||||||
if (meta_window_is_ancestor_of_transient (window->display->focus_window,
|
if (meta_window_is_ancestor_of_transient (window->display->focus_window,
|
||||||
window))
|
window))
|
||||||
{
|
{
|
||||||
@ -1778,7 +1816,11 @@ meta_window_show (MetaWindow *window)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
window->wm_state_demands_attention = TRUE;
|
/* Only set the demands attention hint if the window doesn't
|
||||||
|
* take focus on map and it isn't placed on top on map.
|
||||||
|
*/
|
||||||
|
if (!place_on_top_on_map)
|
||||||
|
window->wm_state_demands_attention = TRUE;
|
||||||
|
|
||||||
/* Prevent EnterNotify events in sloppy/mouse focus from
|
/* Prevent EnterNotify events in sloppy/mouse focus from
|
||||||
* erroneously focusing the window that had been denied
|
* erroneously focusing the window that had been denied
|
||||||
|
Loading…
Reference in New Issue
Block a user