Add WM_NAME rule matching

This commit is contained in:
Matt Vollrath 2020-05-11 21:03:02 -04:00 committed by Bastien Dejean
parent 273e5097b1
commit 6db8831e30
5 changed files with 25 additions and 6 deletions

View file

@ -1041,12 +1041,12 @@ rule \fICOMMANDS\fR
\fBCommands\fR
.RS 4
.PP
\fB\-a\fR, \fB\-\-add\fR (<class_name>|*)[:(<instance_name>|*)] [\fB\-o\fR|\fB\-\-one\-shot\fR] [monitor=MONITOR_SEL|desktop=DESKTOP_SEL|node=NODE_SEL] [state=STATE] [layer=LAYER] [split_dir=DIR] [split_ratio=RATIO] [(hidden|sticky|private|locked|marked|center|follow|manage|focus|border)=(on|off)] [rectangle=WxH+X+Y]
\fB\-a\fR, \fB\-\-add\fR (<class_name>|*)[:(<instance_name>|*)][:(<name>|*)] [\fB\-o\fR|\fB\-\-one\-shot\fR] [monitor=MONITOR_SEL|desktop=DESKTOP_SEL|node=NODE_SEL] [state=STATE] [layer=LAYER] [split_dir=DIR] [split_ratio=RATIO] [(hidden|sticky|private|locked|marked|center|follow|manage|focus|border)=(on|off)] [rectangle=WxH+X+Y]
.RS 4
Create a new rule\&.
.RE
.PP
\fB\-r\fR, \fB\-\-remove\fR ^<n>|head|tail|(<class_name>|*)[:(<instance_name>|*)]\&...
\fB\-r\fR, \fB\-\-remove\fR ^<n>|head|tail|(<class_name>|*)[:(<instance_name>|*)][:(<name>|*)]\&...
.RS 4
Remove the given rules\&.
.RE

View file

@ -1138,8 +1138,10 @@ void cmd_rule(char **args, int num, FILE *rsp)
rule_t *rule = make_rule();
char *class_name = strtok(*args, COL_TOK);
char *instance_name = strtok(NULL, COL_TOK);
char *name = strtok(NULL, COL_TOK);
snprintf(rule->class_name, sizeof(rule->class_name), "%s", class_name);
snprintf(rule->instance_name, sizeof(rule->instance_name), "%s", instance_name==NULL?MATCH_ANY:instance_name);
snprintf(rule->name, sizeof(rule->name), "%s", name==NULL?MATCH_ANY:name);
num--, args++;
size_t i = 0;
while (num > 0) {

View file

@ -39,7 +39,7 @@
rule_t *make_rule(void)
{
rule_t *r = calloc(1, sizeof(rule_t));
r->class_name[0] = r->instance_name[0] = r->effect[0] = '\0';
r->class_name[0] = r->instance_name[0] = r->name[0] = r->effect[0] = '\0';
r->next = r->prev = NULL;
r->one_shot = false;
return r;
@ -83,10 +83,12 @@ void remove_rule_by_cause(char *cause)
rule_t *r = rule_head;
char *class_name = strtok(cause, COL_TOK);
char *instance_name = strtok(NULL, COL_TOK);
char *name = strtok(NULL, COL_TOK);
while (r != NULL) {
rule_t *next = r->next;
if ((class_name != NULL && (streq(class_name, MATCH_ANY) || streq(r->class_name, class_name))) &&
(instance_name == NULL || streq(instance_name, MATCH_ANY) || streq(r->instance_name, instance_name))) {
(instance_name == NULL || streq(instance_name, MATCH_ANY) || streq(r->instance_name, instance_name)) &&
(name == NULL || streq(name, MATCH_ANY) || streq(r->name, name))) {
remove_rule(r);
}
r = next;
@ -281,6 +283,15 @@ void _apply_class(xcb_window_t win, rule_consequence_t *csq)
}
}
void _apply_name(xcb_window_t win, rule_consequence_t *csq)
{
xcb_icccm_get_text_property_reply_t reply;
if (xcb_icccm_get_wm_name_reply(dpy, xcb_icccm_get_wm_name(dpy, win), &reply, NULL) == 1) {
snprintf(csq->name, sizeof(csq->name), "%s", reply.name);
xcb_icccm_get_text_property_reply_wipe(&reply);
}
}
void parse_keys_values(char *buf, rule_consequence_t *csq)
{
char *key = strtok(buf, CSQ_BLK);
@ -299,12 +310,14 @@ void apply_rules(xcb_window_t win, rule_consequence_t *csq)
_apply_transient(win, csq);
_apply_hints(win, csq);
_apply_class(win, csq);
_apply_name(win, csq);
rule_t *rule = rule_head;
while (rule != NULL) {
rule_t *next = rule->next;
if ((streq(rule->class_name, MATCH_ANY) || streq(rule->class_name, csq->class_name)) &&
(streq(rule->instance_name, MATCH_ANY) || streq(rule->instance_name, csq->instance_name))) {
(streq(rule->instance_name, MATCH_ANY) || streq(rule->instance_name, csq->instance_name)) &&
(streq(rule->name, MATCH_ANY) || streq(rule->name, csq->name))) {
char effect[MAXLEN];
snprintf(effect, sizeof(effect), "%s", rule->effect);
parse_keys_values(effect, csq);
@ -424,6 +437,6 @@ void parse_key_value(char *key, char *value, rule_consequence_t *csq)
void list_rules(FILE *rsp)
{
for (rule_t *r = rule_head; r != NULL; r = r->next) {
fprintf(rsp, "%s:%s %c> %s\n", r->class_name, r->instance_name, r->one_shot?'-':'=', r->effect);
fprintf(rsp, "%s:%s:%s %c> %s\n", r->class_name, r->instance_name, r->name, r->one_shot?'-':'=', r->effect);
}
}

View file

@ -44,6 +44,7 @@ void _apply_window_state(xcb_window_t win, rule_consequence_t *csq);
void _apply_transient(xcb_window_t win, rule_consequence_t *csq);
void _apply_hints(xcb_window_t win, rule_consequence_t *csq);
void _apply_class(xcb_window_t win, rule_consequence_t *csq);
void _apply_name(xcb_window_t win, rule_consequence_t *csq);
void parse_keys_values(char *buf, rule_consequence_t *csq);
void apply_rules(xcb_window_t win, rule_consequence_t *csq);
bool schedule_rules(xcb_window_t win, rule_consequence_t *csq);

View file

@ -210,6 +210,7 @@ struct icccm_props_t {
typedef struct {
char class_name[3 * SMALEN / 2];
char instance_name[3 * SMALEN / 2];
char name[3 * SMALEN / 2];
unsigned int border_width;
bool urgent;
bool shown;
@ -341,6 +342,7 @@ typedef struct rule_t rule_t;
struct rule_t {
char class_name[MAXLEN];
char instance_name[MAXLEN];
char name[MAXLEN];
char effect[MAXLEN];
bool one_shot;
rule_t *prev;
@ -350,6 +352,7 @@ struct rule_t {
typedef struct {
char class_name[3 * SMALEN / 2];
char instance_name[3 * SMALEN / 2];
char name[3 * SMALEN / 2];
char monitor_desc[MAXLEN];
char desktop_desc[MAXLEN];
char node_desc[MAXLEN];