mirror of
https://github.com/labwc/labwc.git
synced 2026-03-05 01:40:24 -05:00
window-rules: support matchOnce attribute
...allowing a rule to be applied to only the first window matching a
particular criteria. For example, the following can be used to apply a
window rule to lxqt-panel but not its configuration window with the same
app_id:
<windowRules>
<windowRule identifier="lxqt-panel" matchOnce="true">
<skipTaskbar>yes</skipTaskbar>
<action name="MoveTo" x="0" y="0" />
<action name="ToggleAlwaysOnTop"/>
</windowRule>
</windowRules>
This commit is contained in:
parent
f6c3a3d7c3
commit
41de529fff
5 changed files with 73 additions and 15 deletions
|
|
@ -415,9 +415,9 @@ defined as shown below.
|
||||||
</windowRules>
|
</windowRules>
|
||||||
```
|
```
|
||||||
|
|
||||||
*Actions*
|
*Criteria*
|
||||||
|
|
||||||
*<windowRules><windowRule identifier="" title="">*
|
*<windowRules><windowRule identifier="" title="" matchOnce="">*
|
||||||
Define a window rule for any window which matches the criteria defined
|
Define a window rule for any window which matches the criteria defined
|
||||||
by the attributes *identifier* or *title*. If both are defined, AND
|
by the attributes *identifier* or *title*. If both are defined, AND
|
||||||
logic is used, so both have to match.
|
logic is used, so both have to match.
|
||||||
|
|
@ -429,6 +429,9 @@ defined as shown below.
|
||||||
|
|
||||||
*title* is the title of the window.
|
*title* is the title of the window.
|
||||||
|
|
||||||
|
*matchOnce* can be true|false. If true, the rule will only apply to the
|
||||||
|
first instance of the window with the specified identifier or title.
|
||||||
|
|
||||||
*Properties*
|
*Properties*
|
||||||
|
|
||||||
Property values can be *yes*, *no* or *default*.
|
Property values can be *yes*, *no* or *default*.
|
||||||
|
|
|
||||||
|
|
@ -391,20 +391,41 @@
|
||||||
</libinput>
|
</libinput>
|
||||||
|
|
||||||
<!--
|
<!--
|
||||||
Window Rules
|
# Window Rules
|
||||||
- Criteria can consist of 'identifier' or 'title' or both (in which case
|
# - Criteria can consist of 'identifier' or 'title' or both (in which case
|
||||||
AND logic is used).
|
# AND logic is used).
|
||||||
- 'identifier' relates to app_id for native Wayland windows and WM_CLASS
|
# - 'identifier' relates to app_id for native Wayland windows and WM_CLASS
|
||||||
for XWayland clients.
|
# for XWayland clients.
|
||||||
- Matching against patterns with '*' (wildcard) and '?' (joker) is
|
# - Criteria can also contain `matchOnce="true"` meaning that the rule
|
||||||
supported. Pattern matching is case-insensitive.
|
# must only apply to the first instance of the window with that
|
||||||
|
# particular 'identifier' or 'title'.
|
||||||
|
# - Matching against patterns with '*' (wildcard) and '?' (joker) is
|
||||||
|
# supported. Pattern matching is case-insensitive.
|
||||||
|
|
||||||
<windowRules>
|
<windowRules>
|
||||||
<windowRule identifier="*"><action name="Maximize"/></windowRule>
|
<windowRule identifier="*"><action name="Maximize"/></windowRule>
|
||||||
<windowRule identifier="foo" serverDecoration="yes"/>
|
<windowRule identifier="foo" serverDecoration="yes"/>
|
||||||
<windowRule title="bar" serverDecoration="yes"/>
|
<windowRule title="bar" serverDecoration="yes"/>
|
||||||
<windowRule identifier="baz" title="quax" serverDecoration="yes"/>
|
<windowRule identifier="baz" title="quax" serverDecoration="yes"/>
|
||||||
</windowRules>
|
</windowRules>
|
||||||
|
|
||||||
|
# Example below for `lxqt-panel` and `pcmanfm-qt \-\-desktop`
|
||||||
|
# where 'matchOnce' is used to avoid applying rule to the panel configuration
|
||||||
|
# window with the same 'app_id'
|
||||||
|
|
||||||
|
<windowRules>
|
||||||
|
<windowRule identifier="lxqt-panel" matchOnce="true">
|
||||||
|
<skipTaskbar>yes</skipTaskbar>
|
||||||
|
<action name="MoveTo" x="0" y="0" />
|
||||||
|
<action name="ToggleAlwaysOnTop"/>
|
||||||
|
</windowRule>
|
||||||
|
<windowRule title="pcmanfm-desktop*">
|
||||||
|
<skipTaskbar>yes</skipTaskbar>
|
||||||
|
<skipWindowSwitcher>yes</skipWindowSwitcher>
|
||||||
|
<action name="MoveTo" x="0" y="0" />
|
||||||
|
<action name="ToggleAlwaysOnBottom"/>
|
||||||
|
</windowRule>
|
||||||
|
</windowRules>
|
||||||
-->
|
-->
|
||||||
|
|
||||||
</labwc_config>
|
</labwc_config>
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,7 @@ enum property {
|
||||||
struct window_rule {
|
struct window_rule {
|
||||||
char *identifier;
|
char *identifier;
|
||||||
char *title;
|
char *title;
|
||||||
|
bool match_once;
|
||||||
|
|
||||||
enum window_rule_event event;
|
enum window_rule_event event;
|
||||||
struct wl_list actions;
|
struct wl_list actions;
|
||||||
|
|
|
||||||
|
|
@ -130,6 +130,8 @@ fill_window_rule(char *nodename, char *content)
|
||||||
} else if (!strcmp(nodename, "title")) {
|
} else if (!strcmp(nodename, "title")) {
|
||||||
free(current_window_rule->title);
|
free(current_window_rule->title);
|
||||||
current_window_rule->title = xstrdup(content);
|
current_window_rule->title = xstrdup(content);
|
||||||
|
} else if (!strcasecmp(nodename, "matchOnce")) {
|
||||||
|
set_bool(content, ¤t_window_rule->match_once);
|
||||||
|
|
||||||
/* Event */
|
/* Event */
|
||||||
} else if (!strcmp(nodename, "event")) {
|
} else if (!strcmp(nodename, "event")) {
|
||||||
|
|
|
||||||
|
|
@ -14,6 +14,33 @@
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "window-rules.h"
|
#include "window-rules.h"
|
||||||
|
|
||||||
|
static bool
|
||||||
|
other_instances_exist(struct view *self, const char *id, const char *title)
|
||||||
|
{
|
||||||
|
struct wl_list *views = &self->server->views;
|
||||||
|
const char *prop = NULL;
|
||||||
|
struct view *view;
|
||||||
|
|
||||||
|
wl_list_for_each(view, views, link) {
|
||||||
|
if (view == self) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (id) {
|
||||||
|
prop = view_get_string_prop(view, "app_id");
|
||||||
|
if (prop && !strcmp(prop, id)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (title) {
|
||||||
|
prop = view_get_string_prop(view, "title");
|
||||||
|
if (prop && !strcmp(prop, title)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/* Try to match against identifier AND title (if set) */
|
/* Try to match against identifier AND title (if set) */
|
||||||
static bool
|
static bool
|
||||||
view_matches_criteria(struct window_rule *rule, struct view *view)
|
view_matches_criteria(struct window_rule *rule, struct view *view)
|
||||||
|
|
@ -21,6 +48,10 @@ view_matches_criteria(struct window_rule *rule, struct view *view)
|
||||||
const char *id = view_get_string_prop(view, "app_id");
|
const char *id = view_get_string_prop(view, "app_id");
|
||||||
const char *title = view_get_string_prop(view, "title");
|
const char *title = view_get_string_prop(view, "title");
|
||||||
|
|
||||||
|
if (rule->match_once && other_instances_exist(view, id, title)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
if (rule->identifier && rule->title) {
|
if (rule->identifier && rule->title) {
|
||||||
if (!id || !title) {
|
if (!id || !title) {
|
||||||
return false;
|
return false;
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue