diff --git a/src/bin/e_bg.c b/src/bin/e_bg.c index dc130c526..714c5be96 100644 --- a/src/bin/e_bg.c +++ b/src/bin/e_bg.c @@ -98,8 +98,8 @@ e_bg_zone_update(E_Zone *zone, E_Bg_Transition transition) edje_object_file_get(zone->prev_bg_object, &pfile, &pgroup); edje_object_file_get(zone->bg_object, &file, &group); - if ((pfile) && (file) && (!strcmp(pfile, file)) && - (pgroup) && (group) && (!strcmp(pgroup, group))) + if ((!e_util_strcmp(pfile, file)) && + (!e_util_strcmp(pgroup, group))) { evas_object_del(zone->bg_object); zone->bg_object = zone->prev_bg_object; diff --git a/src/bin/e_border.c b/src/bin/e_border.c index f26d10eaa..7e597d5df 100644 --- a/src/bin/e_border.c +++ b/src/bin/e_border.c @@ -5160,6 +5160,32 @@ _e_border_menu_cb_remember_match_role(void *data, E_Menu *m, E_Menu_Item *mi) e_config_save_queue(); } +static void +_e_border_menu_cb_remember_match_type(void *data, E_Menu *m, E_Menu_Item *mi) +{ + E_Border *bd; + bd = data; + if (!bd->remember) return; + if (e_menu_item_toggle_get(mi)) + bd->remember->match |= E_REMEMBER_MATCH_TYPE; + else + bd->remember->match &= ~E_REMEMBER_MATCH_TYPE; + e_config_save_queue(); +} + +static void +_e_border_menu_cb_remember_match_transient(void *data, E_Menu *m, E_Menu_Item *mi) +{ + E_Border *bd; + bd = data; + if (!bd->remember) return; + if (e_menu_item_toggle_get(mi)) + bd->remember->match |= E_REMEMBER_MATCH_TRANSIENT; + else + bd->remember->match &= ~E_REMEMBER_MATCH_TRANSIENT; + e_config_save_queue(); +} + static void _e_border_menu_cb_remember_apply_pos(void *data, E_Menu *m, E_Menu_Item *mi) { @@ -5364,6 +5390,8 @@ _e_border_menu_show(E_Border *bd, Evas_Coord x, Evas_Coord y, int key) NEW_REMEMBER_MI(_("Match by class"), match, E_REMEMBER_MATCH_CLASS, _e_border_menu_cb_remember_match_class); NEW_REMEMBER_MI(_("Match by title"), match, E_REMEMBER_MATCH_TITLE, _e_border_menu_cb_remember_match_title); NEW_REMEMBER_MI(_("Match by role"), match, E_REMEMBER_MATCH_ROLE, _e_border_menu_cb_remember_match_role); + NEW_REMEMBER_MI(_("Match by window type"), match, E_REMEMBER_MATCH_TYPE, _e_border_menu_cb_remember_match_type); + NEW_REMEMBER_MI(_("Match by transient status"), match, E_REMEMBER_MATCH_TRANSIENT, _e_border_menu_cb_remember_match_transient); mi = e_menu_item_new(m); e_menu_item_separator_set(mi, 1); NEW_REMEMBER_MI(_("Remember position"), apply, E_REMEMBER_APPLY_POS, _e_border_menu_cb_remember_apply_pos); diff --git a/src/bin/e_config.c b/src/bin/e_config.c index 534eb00ff..69ba42daa 100644 --- a/src/bin/e_config.c +++ b/src/bin/e_config.c @@ -126,6 +126,8 @@ e_config_init(void) E_CONFIG_VAL(D, T, class, STR); E_CONFIG_VAL(D, T, title, STR); E_CONFIG_VAL(D, T, role, STR); + E_CONFIG_VAL(D, T, type, INT); + E_CONFIG_VAL(D, T, transient, UCHAR); E_CONFIG_VAL(D, T, apply, INT); E_CONFIG_VAL(D, T, prop.pos_x, INT); E_CONFIG_VAL(D, T, prop.pos_y, INT); diff --git a/src/bin/e_remember.c b/src/bin/e_remember.c index 402ec13e1..64a25c96d 100644 --- a/src/bin/e_remember.c +++ b/src/bin/e_remember.c @@ -6,6 +6,10 @@ /* local subsystem functions */ static void _e_remember_free(E_Remember *rem); +/* FIXME: match netwm window type + * FIXME: match transient (is it a transient for something or not) + */ + /* local subsystem globals */ /* externally accessible functions */ @@ -95,24 +99,34 @@ e_remember_find(E_Border *bd) if (rem->match & E_REMEMBER_MATCH_CLASS) required_matches++; if (rem->match & E_REMEMBER_MATCH_TITLE) required_matches++; if (rem->match & E_REMEMBER_MATCH_ROLE) required_matches++; + if (rem->match & E_REMEMBER_MATCH_TYPE) required_matches++; + if (rem->match & E_REMEMBER_MATCH_TRANSIENT) required_matches++; if (bd->client.netwm.name) title = bd->client.netwm.name; else title = bd->client.icccm.title; if ((rem->match & E_REMEMBER_MATCH_NAME) && - (bd->client.icccm.name) && (rem->name) && - (!strcmp(rem->name, bd->client.icccm.name))) + ((!e_util_strcmp(rem->name, bd->client.icccm.name)) || + (e_util_both_str_empty(rem->name, bd->client.icccm.name)))) matches++; if ((rem->match & E_REMEMBER_MATCH_CLASS) && - (bd->client.icccm.class) && (rem->class) && - (!strcmp(rem->class, bd->client.icccm.class))) + ((!e_util_strcmp(rem->class, bd->client.icccm.class)) || + (e_util_both_str_empty(rem->class, bd->client.icccm.class)))) matches++; if ((rem->match & E_REMEMBER_MATCH_TITLE) && - (title) && (rem->title) && (!strcmp(rem->title, title))) + ((!e_util_strcmp(rem->title, title)) || + (e_util_both_str_empty(rem->title, title)))) matches++; if ((rem->match & E_REMEMBER_MATCH_ROLE) && - (bd->client.icccm.window_role) && (rem->role) && - (!strcmp(rem->role, bd->client.icccm.window_role))) + ((!e_util_strcmp(rem->role, bd->client.icccm.window_role)) || + (e_util_both_str_empty(rem->role, bd->client.icccm.window_role)))) + matches++; + if ((rem->match & E_REMEMBER_MATCH_TYPE) && + (rem->type == bd->client.netwm.type)) + matches++; + if ((rem->match & E_REMEMBER_MATCH_TRANSIENT) && + (((rem->transient) && (bd->client.icccm.transient_for != 0)) || + ((!rem->transient) && (bd->client.icccm.transient_for == 0)))) matches++; if ((matches >= required_matches) && (!rem->delete_me)) return rem; @@ -125,8 +139,7 @@ e_remember_update(E_Remember *rem, E_Border *bd) { IF_FREE(rem->name); IF_FREE(rem->class); - /* only match title the first time - never change it later */ - /* IF_FREE(rem->title); */ + IF_FREE(rem->title); IF_FREE(rem->role); IF_FREE(rem->prop.border); IF_FREE(rem->prop.command); @@ -135,15 +148,19 @@ e_remember_update(E_Remember *rem, E_Border *bd) rem->name = strdup(bd->client.icccm.name); if (bd->client.icccm.class) rem->class = strdup(bd->client.icccm.class); - /* only match title the first time - never change it later */ - /* if (bd->client.netwm.name) rem->title = strdup(bd->client.netwm.name); else if (bd->client.icccm.title) rem->title = strdup(bd->client.icccm.title); - */ if (bd->client.icccm.window_role) rem->role = strdup(bd->client.icccm.window_role); + + rem->type = bd->client.netwm.type; + + if (bd->client.icccm.transient_for != 0) + rem->transient = 1; + else + rem->transient = 0; rem->prop.pos_x = bd->x - bd->zone->x; rem->prop.pos_y = bd->y - bd->zone->y; diff --git a/src/bin/e_remember.h b/src/bin/e_remember.h index 14398be92..1ce192fc7 100644 --- a/src/bin/e_remember.h +++ b/src/bin/e_remember.h @@ -9,6 +9,8 @@ typedef struct _E_Remember E_Remember; #define E_REMEMBER_MATCH_CLASS (1 << 1) #define E_REMEMBER_MATCH_TITLE (1 << 2) #define E_REMEMBER_MATCH_ROLE (1 << 3) +#define E_REMEMBER_MATCH_TYPE (1 << 4) +#define E_REMEMBER_MATCH_TRANSIENT (1 << 5) #define E_REMEMBER_APPLY_POS (1 << 0) #define E_REMEMBER_APPLY_SIZE (1 << 1) @@ -32,6 +34,8 @@ struct _E_Remember unsigned char apply_first_only; int used_count; char *name, *class, *title, *role; + int type; + unsigned char transient; int apply; struct { int pos_x, pos_y; diff --git a/src/bin/e_utils.c b/src/bin/e_utils.c index 8fc82b0b8..ea4092c27 100644 --- a/src/bin/e_utils.c +++ b/src/bin/e_utils.c @@ -215,3 +215,23 @@ e_util_head_exec(int head, char *cmd) } return ok; } + +int +e_util_strcmp(char *s1, char *s2) +{ + if ((s1) && (s2)) + return strcmp(s1, s2); + return 0x7fffffff; +} + +int +e_util_both_str_empty(char *s1, char *s2) +{ + int empty = 0; + + if ((!s1) && (!s2)) return 1; + if ((!s1) || ((s1) && (s1[0] == 0))) empty++; + if ((!s2) || ((s2) && (s2[0] == 0))) empty++; + if (empty == 2) return 1; + return 0; +} diff --git a/src/bin/e_utils.h b/src/bin/e_utils.h index 557f51639..2c0e9d0e5 100644 --- a/src/bin/e_utils.h +++ b/src/bin/e_utils.h @@ -17,6 +17,8 @@ EAPI int e_util_glob_match(char *str, char *glob); EAPI E_Container *e_util_container_number_get(int num); EAPI E_Zone *e_util_container_zone_number_get(int con_num, int zone_num); EAPI int e_util_head_exec(int head, char *cmd); - +EAPI int e_util_strcmp(char *s1, char *s2); +EAPI int e_util_both_str_empty(char *s1, char *s2); + #endif #endif