Add a strict option to the ToggleShowDesktop action
When the strict option is used, normal windows are not able to show themselves while showing the desktop.
This commit is contained in:
parent
adcb7a78d9
commit
7b408bc3b8
7 changed files with 122 additions and 27 deletions
|
@ -176,6 +176,7 @@
|
||||||
<xsd:element minOccurs="0" name="here" type="ob:bool"/>
|
<xsd:element minOccurs="0" name="here" type="ob:bool"/>
|
||||||
<xsd:element minOccurs="0" name="linear" type="ob:bool"/>
|
<xsd:element minOccurs="0" name="linear" type="ob:bool"/>
|
||||||
<xsd:element minOccurs="0" name="group" type="ob:bool"/>
|
<xsd:element minOccurs="0" name="group" type="ob:bool"/>
|
||||||
|
<xsd:element minOccurs="0" name="strict" type="ob:bool"/>
|
||||||
</xsd:all>
|
</xsd:all>
|
||||||
<xsd:attribute name="name" type="ob:actionname" use="required"/>
|
<xsd:attribute name="name" type="ob:actionname" use="required"/>
|
||||||
</xsd:complexType>
|
</xsd:complexType>
|
||||||
|
|
|
@ -1,17 +1,52 @@
|
||||||
#include "openbox/actions.h"
|
#include "openbox/actions.h"
|
||||||
#include "openbox/screen.h"
|
#include "openbox/screen.h"
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
/* If true, windows are unable to be shown while in the showing-desktop
|
||||||
|
state. */
|
||||||
|
gboolean strict;
|
||||||
|
} Options;
|
||||||
|
|
||||||
|
static gpointer setup_func(xmlNodePtr node);
|
||||||
|
static void free_func(gpointer o);
|
||||||
static gboolean run_func(ObActionsData *data, gpointer options);
|
static gboolean run_func(ObActionsData *data, gpointer options);
|
||||||
|
|
||||||
void action_showdesktop_startup(void)
|
void action_showdesktop_startup(void)
|
||||||
{
|
{
|
||||||
actions_register("ToggleShowDesktop", NULL, NULL, run_func);
|
actions_register("ToggleShowDesktop", setup_func, free_func, run_func);
|
||||||
|
}
|
||||||
|
|
||||||
|
static gpointer setup_func(xmlNodePtr node)
|
||||||
|
{
|
||||||
|
xmlNodePtr n;
|
||||||
|
Options *o = g_slice_new0(Options);
|
||||||
|
o->strict = FALSE;
|
||||||
|
|
||||||
|
if ((n = obt_xml_find_node(node, "strict")))
|
||||||
|
o->strict = obt_xml_node_bool(n);
|
||||||
|
|
||||||
|
return o;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void free_func(gpointer o)
|
||||||
|
{
|
||||||
|
g_slice_free(Options, o);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Always return FALSE because its not interactive */
|
/* Always return FALSE because its not interactive */
|
||||||
static gboolean run_func(ObActionsData *data, gpointer options)
|
static gboolean run_func(ObActionsData *data, gpointer options)
|
||||||
{
|
{
|
||||||
screen_show_desktop(!screen_showing_desktop, NULL);
|
Options *o = options;
|
||||||
|
|
||||||
|
ObScreenShowDestopMode show_mode;
|
||||||
|
if (screen_showing_desktop())
|
||||||
|
show_mode = SCREEN_SHOW_DESKTOP_NO;
|
||||||
|
else if (!o->strict)
|
||||||
|
show_mode = SCREEN_SHOW_DESKTOP_UNTIL_WINDOW;
|
||||||
|
else
|
||||||
|
show_mode = SCREEN_SHOW_DESKTOP_UNTIL_TOGGLE;
|
||||||
|
|
||||||
|
screen_show_desktop(show_mode, NULL);
|
||||||
|
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
|
@ -2734,7 +2734,7 @@ gboolean client_should_show(ObClient *self)
|
||||||
{
|
{
|
||||||
if (self->iconic)
|
if (self->iconic)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
if (client_normal(self) && screen_showing_desktop)
|
if (client_normal(self) && screen_showing_desktop())
|
||||||
return FALSE;
|
return FALSE;
|
||||||
if (self->desktop == screen_desktop || self->desktop == DESKTOP_ALL)
|
if (self->desktop == screen_desktop || self->desktop == DESKTOP_ALL)
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
@ -4080,7 +4080,7 @@ gboolean client_focus(ObClient *self)
|
||||||
static void client_present(ObClient *self, gboolean here, gboolean raise,
|
static void client_present(ObClient *self, gboolean here, gboolean raise,
|
||||||
gboolean unshade)
|
gboolean unshade)
|
||||||
{
|
{
|
||||||
if (client_normal(self) && screen_showing_desktop)
|
if (client_normal(self) && screen_showing_desktop())
|
||||||
screen_show_desktop(FALSE, self);
|
screen_show_desktop(FALSE, self);
|
||||||
if (self->iconic)
|
if (self->iconic)
|
||||||
client_iconify(self, FALSE, here, FALSE);
|
client_iconify(self, FALSE, here, FALSE);
|
||||||
|
|
|
@ -772,7 +772,12 @@ static void event_handle_root(XEvent *e)
|
||||||
if (d > 0 && d <= 1000)
|
if (d > 0 && d <= 1000)
|
||||||
screen_set_num_desktops(d);
|
screen_set_num_desktops(d);
|
||||||
} else if (msgtype == OBT_PROP_ATOM(NET_SHOWING_DESKTOP)) {
|
} else if (msgtype == OBT_PROP_ATOM(NET_SHOWING_DESKTOP)) {
|
||||||
screen_show_desktop(e->xclient.data.l[0] != 0, NULL);
|
ObScreenShowDestopMode show_mode;
|
||||||
|
if (e->xclient.data.l[0] != 0)
|
||||||
|
show_mode = SCREEN_SHOW_DESKTOP_UNTIL_WINDOW;
|
||||||
|
else
|
||||||
|
show_mode = SCREEN_SHOW_DESKTOP_NO;
|
||||||
|
screen_show_desktop(show_mode, NULL);
|
||||||
} else if (msgtype == OBT_PROP_ATOM(OB_CONTROL)) {
|
} else if (msgtype == OBT_PROP_ATOM(OB_CONTROL)) {
|
||||||
ob_debug("OB_CONTROL: %d", e->xclient.data.l[0]);
|
ob_debug("OB_CONTROL: %d", e->xclient.data.l[0]);
|
||||||
if (e->xclient.data.l[0] == 1)
|
if (e->xclient.data.l[0] == 1)
|
||||||
|
|
|
@ -406,8 +406,19 @@ static gboolean place_least_overlap(ObClient *c, Rect *head, int *x, int *y,
|
||||||
GSList* potential_overlap_clients = NULL;
|
GSList* potential_overlap_clients = NULL;
|
||||||
gint n_client_rects = config_dock_hide ? 0 : 1;
|
gint n_client_rects = config_dock_hide ? 0 : 1;
|
||||||
|
|
||||||
/* if we're "showing desktop", ignore all existing windows */
|
/* If we're "showing desktop", and going to allow this window to
|
||||||
if (!screen_showing_desktop) {
|
be shown now, then ignore all existing windows */
|
||||||
|
gboolean ignore_windows = FALSE;
|
||||||
|
switch (screen_show_desktop_mode) {
|
||||||
|
case SCREEN_SHOW_DESKTOP_NO:
|
||||||
|
case SCREEN_SHOW_DESKTOP_UNTIL_WINDOW:
|
||||||
|
break;
|
||||||
|
case SCREEN_SHOW_DESKTOP_UNTIL_TOGGLE:
|
||||||
|
ignore_windows = TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!ignore_windows) {
|
||||||
GList* it;
|
GList* it;
|
||||||
for (it = client_list; it != NULL; it = g_list_next(it)) {
|
for (it = client_list; it != NULL; it = g_list_next(it)) {
|
||||||
ObClient* maybe_client = (ObClient*)it->data;
|
ObClient* maybe_client = (ObClient*)it->data;
|
||||||
|
|
|
@ -61,7 +61,7 @@ guint screen_num_desktops;
|
||||||
guint screen_num_monitors;
|
guint screen_num_monitors;
|
||||||
guint screen_desktop;
|
guint screen_desktop;
|
||||||
guint screen_last_desktop;
|
guint screen_last_desktop;
|
||||||
gboolean screen_showing_desktop;
|
ObScreenShowDestopMode screen_show_desktop_mode;
|
||||||
ObDesktopLayout screen_desktop_layout;
|
ObDesktopLayout screen_desktop_layout;
|
||||||
gchar **screen_desktop_names;
|
gchar **screen_desktop_names;
|
||||||
Window screen_support_win;
|
Window screen_support_win;
|
||||||
|
@ -445,9 +445,9 @@ void screen_startup(gboolean reconfig)
|
||||||
screen_last_desktop = screen_desktop;
|
screen_last_desktop = screen_desktop;
|
||||||
|
|
||||||
/* don't start in showing-desktop mode */
|
/* don't start in showing-desktop mode */
|
||||||
screen_showing_desktop = FALSE;
|
screen_show_desktop_mode = SCREEN_SHOW_DESKTOP_NO;
|
||||||
OBT_PROP_SET32(obt_root(ob_screen),
|
OBT_PROP_SET32(obt_root(ob_screen),
|
||||||
NET_SHOWING_DESKTOP, CARDINAL, screen_showing_desktop);
|
NET_SHOWING_DESKTOP, CARDINAL, screen_showing_desktop());
|
||||||
|
|
||||||
if (session_desktop_layout_present &&
|
if (session_desktop_layout_present &&
|
||||||
screen_validate_layout(&session_desktop_layout))
|
screen_validate_layout(&session_desktop_layout))
|
||||||
|
@ -1218,15 +1218,33 @@ void screen_update_desktop_names(void)
|
||||||
screen_num_desktops);
|
screen_num_desktops);
|
||||||
}
|
}
|
||||||
|
|
||||||
void screen_show_desktop(gboolean show, ObClient *show_only)
|
void screen_show_desktop(ObScreenShowDestopMode show_mode, ObClient *show_only)
|
||||||
{
|
{
|
||||||
GList *it;
|
GList *it;
|
||||||
|
|
||||||
if (show == screen_showing_desktop) return; /* no change */
|
ObScreenShowDestopMode before_mode = screen_show_desktop_mode;
|
||||||
|
|
||||||
screen_showing_desktop = show;
|
gboolean showing_before = screen_showing_desktop();
|
||||||
|
screen_show_desktop_mode = show_mode;
|
||||||
|
gboolean showing_after = screen_showing_desktop();
|
||||||
|
|
||||||
if (show) {
|
if (showing_before == showing_after) {
|
||||||
|
/* No change. */
|
||||||
|
screen_show_desktop_mode = before_mode;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (screen_show_desktop_mode == SCREEN_SHOW_DESKTOP_UNTIL_TOGGLE &&
|
||||||
|
show_only != NULL)
|
||||||
|
{
|
||||||
|
/* If we're showing the desktop until the show-mode is toggled, we
|
||||||
|
don't allow breaking out of showing-desktop mode unless we're
|
||||||
|
showing all the windows again. */
|
||||||
|
screen_show_desktop_mode = before_mode;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (showing_after) {
|
||||||
/* hide windows bottom to top */
|
/* hide windows bottom to top */
|
||||||
for (it = g_list_last(stacking_list); it; it = g_list_previous(it)) {
|
for (it = g_list_last(stacking_list); it; it = g_list_previous(it)) {
|
||||||
if (WINDOW_IS_CLIENT(it->data)) {
|
if (WINDOW_IS_CLIENT(it->data)) {
|
||||||
|
@ -1250,7 +1268,7 @@ void screen_show_desktop(gboolean show, ObClient *show_only)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (show) {
|
if (showing_after) {
|
||||||
/* focus the desktop */
|
/* focus the desktop */
|
||||||
for (it = focus_order; it; it = g_list_next(it)) {
|
for (it = focus_order; it; it = g_list_next(it)) {
|
||||||
ObClient *c = it->data;
|
ObClient *c = it->data;
|
||||||
|
@ -1275,8 +1293,23 @@ void screen_show_desktop(gboolean show, ObClient *show_only)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
show = !!show; /* make it boolean */
|
OBT_PROP_SET32(obt_root(ob_screen),
|
||||||
OBT_PROP_SET32(obt_root(ob_screen), NET_SHOWING_DESKTOP, CARDINAL, show);
|
NET_SHOWING_DESKTOP,
|
||||||
|
CARDINAL,
|
||||||
|
!!showing_after);
|
||||||
|
}
|
||||||
|
|
||||||
|
gboolean screen_showing_desktop()
|
||||||
|
{
|
||||||
|
switch (screen_show_desktop_mode) {
|
||||||
|
case SCREEN_SHOW_DESKTOP_NO:
|
||||||
|
return FALSE;
|
||||||
|
case SCREEN_SHOW_DESKTOP_UNTIL_WINDOW:
|
||||||
|
case SCREEN_SHOW_DESKTOP_UNTIL_TOGGLE:
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
g_assert_not_reached();
|
||||||
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
void screen_install_colormap(ObClient *client, gboolean install)
|
void screen_install_colormap(ObClient *client, gboolean install)
|
||||||
|
|
|
@ -26,6 +26,12 @@ struct _ObClient;
|
||||||
|
|
||||||
#define DESKTOP_ALL (0xffffffff)
|
#define DESKTOP_ALL (0xffffffff)
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
SCREEN_SHOW_DESKTOP_NO,
|
||||||
|
SCREEN_SHOW_DESKTOP_UNTIL_WINDOW,
|
||||||
|
SCREEN_SHOW_DESKTOP_UNTIL_TOGGLE
|
||||||
|
} ObScreenShowDestopMode;
|
||||||
|
|
||||||
/*! The number of available desktops */
|
/*! The number of available desktops */
|
||||||
extern guint screen_num_desktops;
|
extern guint screen_num_desktops;
|
||||||
/*! The number of virtual "xinerama" screens/heads */
|
/*! The number of virtual "xinerama" screens/heads */
|
||||||
|
@ -35,7 +41,7 @@ extern guint screen_desktop;
|
||||||
/*! The desktop which was last visible */
|
/*! The desktop which was last visible */
|
||||||
extern guint screen_last_desktop;
|
extern guint screen_last_desktop;
|
||||||
/*! Are we in showing-desktop mode? */
|
/*! Are we in showing-desktop mode? */
|
||||||
extern gboolean screen_showing_desktop;
|
extern ObScreenShowDestopMode screen_show_desktop_mode;
|
||||||
/*! The support window also used for focus and stacking */
|
/*! The support window also used for focus and stacking */
|
||||||
extern Window screen_support_win;
|
extern Window screen_support_win;
|
||||||
/*! The last time at which the user changed desktops */
|
/*! The last time at which the user changed desktops */
|
||||||
|
@ -90,7 +96,11 @@ void screen_hide_desktop_popup(void);
|
||||||
show is FALSE (restoring from show-desktop mode), and the rest are
|
show is FALSE (restoring from show-desktop mode), and the rest are
|
||||||
iconified.
|
iconified.
|
||||||
*/
|
*/
|
||||||
void screen_show_desktop(gboolean show, struct _ObClient *show_only);
|
void screen_show_desktop(ObScreenShowDestopMode show_mode,
|
||||||
|
struct _ObClient *show_only);
|
||||||
|
|
||||||
|
/*! Returns true if showing desktop mode is enabled. */
|
||||||
|
gboolean screen_showing_desktop();
|
||||||
|
|
||||||
/*! Updates the desktop layout from the root property if available */
|
/*! Updates the desktop layout from the root property if available */
|
||||||
void screen_update_layout(void);
|
void screen_update_layout(void);
|
||||||
|
|
Loading…
Reference in a new issue