summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--data/rc.xml2
-rw-r--r--obt/prop.c2
-rw-r--r--obt/prop.h2
-rw-r--r--openbox/client.c35
-rw-r--r--openbox/client.h4
-rw-r--r--openbox/config.c28
-rw-r--r--openbox/config.h2
-rw-r--r--openbox/screen.c2
8 files changed, 71 insertions, 6 deletions
diff --git a/data/rc.xml b/data/rc.xml
index 209cc2dc..7c37928e 100644
--- a/data/rc.xml
+++ b/data/rc.xml
@@ -652,6 +652,8 @@
<application name="the window's _OB_APP_NAME property (see obxprop)"
class="the window's _OB_APP_CLASS property (see obxprop)"
+ groupname="the window's _OB_APP_GROUP_NAME property (see obxprop)"
+ groupclass="the window's _OB_APP_GROUP_CLASS property (see obxprop)"
role="the window's _OB_APP_ROLE property (see obxprop)"
title="the window's _OB_APP_TITLE property (see obxprop)"
type="the window's _OB_APP_TYPE property (see obxprob)..
diff --git a/obt/prop.c b/obt/prop.c
index 638373fd..f7919d6c 100644
--- a/obt/prop.c
+++ b/obt/prop.c
@@ -197,6 +197,8 @@ void obt_prop_startup(void)
CREATE_(OB_APP_TITLE);
CREATE_(OB_APP_NAME);
CREATE_(OB_APP_CLASS);
+ CREATE_(OB_APP_GROUP_NAME);
+ CREATE_(OB_APP_GROUP_CLASS);
CREATE_(OB_APP_TYPE);
}
diff --git a/obt/prop.h b/obt/prop.h
index b30232e9..acb5c956 100644
--- a/obt/prop.h
+++ b/obt/prop.h
@@ -219,6 +219,8 @@ typedef enum {
OBT_PROP_OB_APP_TITLE,
OBT_PROP_OB_APP_NAME,
OBT_PROP_OB_APP_CLASS,
+ OBT_PROP_OB_APP_GROUP_NAME,
+ OBT_PROP_OB_APP_GROUP_CLASS,
OBT_PROP_OB_APP_TYPE,
OBT_PROP_NUM_ATOMS
diff --git a/openbox/client.c b/openbox/client.c
index c54b21fb..cd93ba59 100644
--- a/openbox/client.c
+++ b/openbox/client.c
@@ -250,6 +250,8 @@ void client_manage(Window window, ObPrompt *prompt)
ob_debug("Window group: 0x%x", self->group?self->group->leader:0);
ob_debug("Window name: %s class: %s role: %s title: %s",
self->name, self->class, self->role, self->title);
+ ob_debug("Window group name: %s group class: %s",
+ self->group_name, self->group_class);
/* per-app settings override stuff from client_get_all, and return the
settings for other uses too. the returned settings is a shallow copy,
@@ -723,6 +725,8 @@ void client_unmanage(ObClient *self)
g_free(self->name);
g_free(self->class);
g_free(self->role);
+ g_free(self->group_name);
+ g_free(self->group_class);
g_free(self->client_machine);
g_free(self->sm_client_id);
g_slice_free(ObClient, self);
@@ -915,15 +919,25 @@ static ObAppSettings *client_get_settings_state(ObClient *self)
g_assert(app->name != NULL || app->class != NULL ||
app->role != NULL || app->title != NULL ||
+ app->group_name != NULL || app->group_class != NULL ||
(signed)app->type >= 0);
if (app->name &&
!g_pattern_match(app->name, strlen(self->name), self->name, NULL))
match = FALSE;
+ else if (app->group_name &&
+ !g_pattern_match(app->group_name,
+ strlen(self->group_name), self->group_name, NULL))
+ match = FALSE;
else if (app->class &&
!g_pattern_match(app->class,
strlen(self->class), self->class, NULL))
match = FALSE;
+ else if (app->group_class &&
+ !g_pattern_match(app->group_class,
+ strlen(self->group_class), self->group_class,
+ NULL))
+ match = FALSE;
else if (app->role &&
!g_pattern_match(app->role,
strlen(self->role), self->role, NULL))
@@ -2365,6 +2379,25 @@ static void client_get_session_ids(ObClient *self)
if (self->name == NULL) self->name = g_strdup("");
if (self->class == NULL) self->class = g_strdup("");
+ /* get the WM_CLASS (name and class) from the group leader. make them "" if
+ they are not provided */
+ if (leader)
+ got = OBT_PROP_GETSS_TYPE(leader, WM_CLASS, STRING_NO_CC, &ss);
+ else
+ got = FALSE;
+
+ if (got) {
+ if (ss[0]) {
+ self->group_name = g_strdup(ss[0]);
+ if (ss[1])
+ self->group_class = g_strdup(ss[1]);
+ }
+ g_strfreev(ss);
+ }
+
+ if (self->group_name == NULL) self->group_name = g_strdup("");
+ if (self->group_class == NULL) self->group_class = g_strdup("");
+
/* get the WM_WINDOW_ROLE. make it "" if it is not provided */
got = OBT_PROP_GETS_XPCS(self->window, WM_WINDOW_ROLE, &s);
@@ -2434,6 +2467,8 @@ static void client_save_app_rule_values(ObClient *self)
OBT_PROP_SETS(self->window, OB_APP_ROLE, self->role);
OBT_PROP_SETS(self->window, OB_APP_NAME, self->name);
OBT_PROP_SETS(self->window, OB_APP_CLASS, self->class);
+ OBT_PROP_SETS(self->window, OB_APP_GROUP_NAME, self->group_name);
+ OBT_PROP_SETS(self->window, OB_APP_GROUP_CLASS, self->group_class);
OBT_PROP_SETS(self->window, OB_APP_TITLE, self->original_title);
switch (self->type) {
diff --git a/openbox/client.h b/openbox/client.h
index 5a20822f..0e55c59f 100644
--- a/openbox/client.h
+++ b/openbox/client.h
@@ -127,6 +127,10 @@ struct _ObClient
gchar *class;
/*! The specified role of the window, used for identification */
gchar *role;
+ /*! The application that created the window's group. */
+ gchar *group_name;
+ /*! The class of the window's group, can used for grouping */
+ gchar *group_class;
/*! The session client id for the window. *This can be NULL!* */
gchar *sm_client_id;
diff --git a/openbox/config.c b/openbox/config.c
index 0d9eb689..d5ff8c45 100644
--- a/openbox/config.c
+++ b/openbox/config.c
@@ -215,8 +215,9 @@ static void parse_per_app_settings(xmlNodePtr node, gpointer d)
{
xmlNodePtr app = obt_xml_find_node(node->children, "application");
gchar *name = NULL, *class = NULL, *role = NULL, *title = NULL,
- *type_str = NULL;
- gboolean name_set, class_set, type_set, role_set, title_set;
+ *type_str = NULL, *group_name = NULL, *group_class = NULL;
+ gboolean name_set, class_set, type_set, role_set, title_set,
+ group_name_set, group_class_set;
ObClientType type;
gboolean x_pos_given;
@@ -225,6 +226,8 @@ static void parse_per_app_settings(xmlNodePtr node, gpointer d)
class_set = obt_xml_attr_string(app, "class", &class);
name_set = obt_xml_attr_string(app, "name", &name);
+ group_class_set = obt_xml_attr_string(app, "groupclass", &group_class);
+ group_name_set = obt_xml_attr_string(app, "groupname", &group_name);
type_set = obt_xml_attr_string(app, "type", &type_str);
role_set = obt_xml_attr_string(app, "role", &role);
title_set = obt_xml_attr_string(app, "title", &title);
@@ -251,7 +254,9 @@ static void parse_per_app_settings(xmlNodePtr node, gpointer d)
type_set = FALSE; /* not valid! */
}
- if (class_set || name_set || role_set || title_set || type_set) {
+ if (class_set || name_set || role_set || title_set || type_set ||
+ group_class_set || group_name_set)
+ {
xmlNodePtr n, c;
ObAppSettings *settings = config_create_app_settings();
@@ -261,6 +266,12 @@ static void parse_per_app_settings(xmlNodePtr node, gpointer d)
if (class_set)
settings->class = g_pattern_spec_new(class);
+ if (group_name_set)
+ settings->group_name = g_pattern_spec_new(group_name);
+
+ if (group_class_set)
+ settings->group_class = g_pattern_spec_new(group_class);
+
if (role_set)
settings->role = g_pattern_spec_new(role);
@@ -377,10 +388,13 @@ static void parse_per_app_settings(xmlNodePtr node, gpointer d)
(gpointer) settings);
g_free(name);
g_free(class);
+ g_free(group_name);
+ g_free(group_class);
g_free(role);
g_free(title);
g_free(type_str);
- name = class = role = title = type_str = NULL;
+ name = class = group_name = group_class = role = title = type_str =
+ NULL;
}
app = obt_xml_find_node(app->next, "application");
@@ -1132,10 +1146,12 @@ void config_shutdown(void)
for (it = config_per_app_settings; it; it = g_slist_next(it)) {
ObAppSettings *itd = (ObAppSettings *)it->data;
- if (itd->name) g_pattern_spec_free(itd->name);
- if (itd->role) g_pattern_spec_free(itd->role);
+ if (itd->name) g_pattern_spec_free(itd->name);
+ if (itd->role) g_pattern_spec_free(itd->role);
if (itd->title) g_pattern_spec_free(itd->title);
if (itd->class) g_pattern_spec_free(itd->class);
+ if (itd->group_name) g_pattern_spec_free(itd->group_name);
+ if (itd->group_class) g_pattern_spec_free(itd->group_class);
g_slice_free(ObAppSettings, it->data);
}
g_slist_free(config_per_app_settings);
diff --git a/openbox/config.h b/openbox/config.h
index 730dc39a..43386d3c 100644
--- a/openbox/config.h
+++ b/openbox/config.h
@@ -38,6 +38,8 @@ struct _ObAppSettings
GPatternSpec *class;
GPatternSpec *name;
GPatternSpec *role;
+ GPatternSpec *group_class;
+ GPatternSpec *group_name;
GPatternSpec *title;
ObClientType type;
diff --git a/openbox/screen.c b/openbox/screen.c
index f4031f59..33acb4a1 100644
--- a/openbox/screen.c
+++ b/openbox/screen.c
@@ -305,6 +305,8 @@ gboolean screen_annex(void)
supported[i++] = OBT_PROP_ATOM(OB_APP_TITLE);
supported[i++] = OBT_PROP_ATOM(OB_APP_NAME);
supported[i++] = OBT_PROP_ATOM(OB_APP_CLASS);
+ supported[i++] = OBT_PROP_ATOM(OB_APP_GROUP_NAME);
+ supported[i++] = OBT_PROP_ATOM(OB_APP_GROUP_CLASS);
supported[i++] = OBT_PROP_ATOM(OB_APP_TYPE);
g_assert(i == num_support);