diff --git a/src/Makefile.am b/src/Makefile.am index 8aa011397..e4891bc5a 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -27,6 +27,7 @@ enlightenment_SOURCES = \ actions.h actions.c \ background.h background.c \ border.h border.c \ + bordermenu.h bordermenu.c \ config.h config.c \ cursors.c cursors.h \ debug.c debug.h \ diff --git a/src/actions.c b/src/actions.c index 0584c1691..683baeaea 100644 --- a/src/actions.c +++ b/src/actions.c @@ -9,6 +9,7 @@ #include "view.h" #include "util.h" #include "guides.h" +#include "bordermenu.h" static Evas_List action_impls = NULL; static Evas_List current_actions = NULL; @@ -1531,6 +1532,8 @@ e_act_menu_start (E_Object *object, E_Action *a, void *data, int x, int y, int r if (!b) D_RETURN; if (b->client.is_desktop) D_RETURN; + e_bordermenu_do(b); + D_RETURN; UN(a); UN(data); diff --git a/src/border.c b/src/border.c index 97693d464..4db6f9961 100644 --- a/src/border.c +++ b/src/border.c @@ -12,6 +12,7 @@ #include "place.h" #include "match.h" #include "focus.h" +#include "menu.h" /* Window border rendering, querying, setting & modification code */ @@ -1215,6 +1216,17 @@ e_border_cleanup(E_Border *b) D_ENTER; + e_match_save_props(b); + + while (b->menus) + { + E_Menu *m; + + m = b->menus->data; + e_menu_hide(m); + e_object_unref(E_OBJECT(m)); + b->menus = evas_list_remove(b->menus, m); + } e_desktops_del_border(b->desk, b); if (b->bits.l) ebits_free(b->bits.l); if (b->bits.r) ebits_free(b->bits.r); diff --git a/src/border.h b/src/border.h index 182f6d84f..9e749ede8 100644 --- a/src/border.h +++ b/src/border.h @@ -107,6 +107,41 @@ struct _E_Border int x, y; } area; int internal; + struct { + int matched; + struct { + int matched; + int ignore; + } prog_location; + struct { + int matched; + char *style; + } border; + struct { + int matched; + int x, y; + } location; + struct { + int matched; + int x, y; + } desk_area; + struct { + int matched; + int w, h; + } size; + struct { + int matched; + int desk; + } desktop; + struct { + int matched; + int sticky; + } sticky; + struct { + int matched; + int layer; + } layer; + } matched; } client; struct { @@ -133,6 +168,8 @@ struct _E_Border int hold_changes; + Evas_List menus; + int changed; }; diff --git a/src/bordermenu.c b/src/bordermenu.c new file mode 100644 index 000000000..cc8357672 --- /dev/null +++ b/src/bordermenu.c @@ -0,0 +1,104 @@ +#include "menu.h" +#include "border.h" +#include "desktops.h" +#include "debug.h" +#include "util.h" +#include "bordermenu.h" + +static void e_bordermenu_cb_close(E_Menu *m, E_Menu_Item *mi, void *data); +static void e_bordermenu_cb_remember_location(E_Menu *m, E_Menu_Item *mi, void *data); + +static void +e_bordermenu_cb_close(E_Menu *m, E_Menu_Item *mi, void *data) +{ + E_Border *b; + + D_ENTER; + + b = data; + + if (b->win.client) e_icccm_delete(b->win.client); + + D_RETURN; + UN(m); + UN(mi); +} + +static void +e_bordermenu_cb_remember_location(E_Menu *m, E_Menu_Item *mi, void *data) +{ + E_Border *b; + + D_ENTER; + + b = data; + + if (mi->on) e_menu_item_set_state(mi, 0); + else e_menu_item_set_state(mi, 1); + e_menu_set_state(m, mi); + + b->client.matched.matched = 1; + b->client.matched.location.matched = mi->on; + + D_RETURN; + UN(m); +} + +void +e_bordermenu_do(E_Border *b) +{ + E_Menu *menu; + E_Menu_Item *menuitem; + + D_ENTER; + if (!b->menus) + { + menu = e_menu_new(); + b->menus = evas_list_append(b->menus, menu); + e_menu_set_padding_icon(menu, 2); + e_menu_set_padding_state(menu, 2); + + menuitem = e_menu_item_new("Close"); + /* e_menu_item_set_icon(menuitem, icon); */ + /* e_menu_item_set_scale_icon(menuitem, 1);*/ + /* e_menu_item_set_separator(menuitem, 1);*/ + e_menu_item_set_callback(menuitem, e_bordermenu_cb_close, b); + e_menu_add_item(menu, menuitem); + + menuitem = e_menu_item_new(""); + e_menu_item_set_separator(menuitem, 1); + e_menu_item_set_check(menuitem, 1); + e_menu_item_set_state(menuitem, b->client.matched.location.matched); + e_menu_item_set_callback(menuitem, e_bordermenu_cb_remember_location, b); + e_menu_add_item(menu, menuitem); + + menuitem = e_menu_item_new("Remember Location"); + e_menu_item_set_check(menuitem, 1); + e_menu_item_set_state(menuitem, b->client.matched.location.matched); + e_menu_item_set_callback(menuitem, e_bordermenu_cb_remember_location, b); + e_menu_add_item(menu, menuitem); + e_menu_set_state(menu, menuitem); + } + + { + int pl, pr, pt, pb; + int crx, cry, crw, crh; + int mx, my; + + menu = b->menus->data; + pl = pr = pt = pb = 0; + if (b->bits.t) ebits_get_insets(b->bits.t, &pl, &pr, &pt, &pb); + crx = b->current.x + pl; + cry = b->current.y + pt; + crw = b->client.w; + crh = b->client.h; + ecore_pointer_xy_get(&mx, &my); + if (mx + menu->current.w > crx + crw) mx = crx + crw - menu->current.w; + if (my + menu->current.h > cry + crh) my = cry + crh - menu->current.h; + if (mx < crx) mx = crx; + if (my < cry) my = cry; + e_menu_show_at_mouse(menu, mx, my, CurrentTime); + } + + D_RETURN; +} diff --git a/src/bordermenu.h b/src/bordermenu.h new file mode 100644 index 000000000..7976dc38a --- /dev/null +++ b/src/bordermenu.h @@ -0,0 +1,9 @@ +#ifndef E_BORDERMENU_H +#define E_BORDERMENU_H + +#include "e.h" + +void e_bordermenu_do(E_Border *b); + +#endif + diff --git a/src/config.c b/src/config.c index 5ce4e83e8..ca07d8872 100644 --- a/src/config.c +++ b/src/config.c @@ -10,6 +10,7 @@ static char cfg_settings_db[PATH_MAX] = ""; static char cfg_actions_db[PATH_MAX] = ""; static char cfg_borders_db[PATH_MAX] = ""; static char cfg_apps_menu_db[PATH_MAX] = ""; +static char cfg_match_db[PATH_MAX] = ""; static char cfg_menus_dir[PATH_MAX] = ""; static char cfg_entries_dir[PATH_MAX] = ""; static char cfg_selections_dir[PATH_MAX] = ""; @@ -60,6 +61,8 @@ e_config_get(char *type) "%s/behavior/actions.db", e_config_user_dir()); E_CONF("apps_menu", cfg_apps_menu_db, "%s/behavior/apps_menu.db", e_config_user_dir()); + E_CONF("match", cfg_match_db, + "%s/behavior/match.db", e_config_user_dir()); E_CONF("borders", cfg_borders_db, PACKAGE_DATA_DIR"/data/borders/"); E_CONF("menus", cfg_menus_dir, @@ -132,6 +135,7 @@ e_config_set_user_dir(char *dir) cfg_actions_db[0] = 0; cfg_borders_db[0] = 0; cfg_apps_menu_db[0]= 0; + cfg_match_db[0]= 0; cfg_menus_dir[0] = 0; cfg_entries_dir[0] = 0; cfg_selections_dir[0] = 0; diff --git a/src/match.c b/src/match.c index f5e0ed788..4cf2d0419 100644 --- a/src/match.c +++ b/src/match.c @@ -1,42 +1,132 @@ #include "debug.h" #include "match.h" +#include "config.h" void e_match_set_props(E_Border *b) { + char buf[PATH_MAX]; + E_DB_File *db; + int ok; + D_ENTER; -#if 0 - /* if we have a match that says to ignore prog coords: */ - b->client.pos.requested = 0; - /* if we have a match that applies a specifi border: */ - IF_FREE(b->border_style); - e_strdup(b->border_style, match_style); - /* if we have a match that specifies a location */ - b->client.pos.requested = 1; - b->client.pos.gravity = NorthWestGravity; - b->client.pos.x = match_x; - b->client.pos.y = match_y; - b->client.no_place = 1; - /* if we have a match specifying desk area (only valid with loc match */ - b->client.pos.x += (match_area_x - b->desk->desk.area.x) * b->desk->real.w; - b->client.pos.y += (match_area_y - b->desk->desk.area.y) * b->desk->real.h; - b->client.area.x = match_area_x; - b->client.area.y = match_area_y; - /* if we have a match specifying a size */ - b->current.requested.w = match_w; - b->current.requested.h = match_h; - ecore_window_resize(b->win.client, match_w, match_h); - /* if we have a match specifying a desktop */ - b->client.desk = match_desk; - e_border_raise(b); - if (b->client.desk != b->desk->desk.desk) b->current.requested.visible = 0; - b->client.no_place = 1; - /* if we have a match specifying stickyness */ - b->client.sticky = match_sticky; - /* if we have a match specifying layer */ - b->client.layer = match_layer; -#endif + if ((!b->client.name) || (!b->client.class)) D_RETURN; + db = e_db_open(e_config_get("match")); + sprintf(buf, "match/%s/%s/match", b->client.name, b->client.class); + ok = e_db_int_get(db, buf, &(b->client.matched.matched)); + if (!ok) + { + e_db_close(db); + D_RETURN; + } + sprintf(buf, "match/%s/%s/prog_location/ignore", b->client.name, b->client.class); + b->client.matched.prog_location.matched = e_db_int_get(db, buf, &(b->client.matched.prog_location.ignore)); + sprintf(buf, "match/%s/%s/border/border", b->client.name, b->client.class); + b->client.matched.border.style = e_db_str_get(db, buf); + b->client.matched.border.matched = (int)b->client.matched.border.style; + sprintf(buf, "match/%s/%s/location/x", b->client.name, b->client.class); + b->client.matched.location.matched = e_db_int_get(db, buf, &(b->client.matched.location.x)); + sprintf(buf, "match/%s/%s/location/y", b->client.name, b->client.class); + b->client.matched.location.matched = e_db_int_get(db, buf, &(b->client.matched.location.y)); + sprintf(buf, "match/%s/%s/desk_area/x", b->client.name, b->client.class); + b->client.matched.desk_area.matched = e_db_int_get(db, buf, &(b->client.matched.desk_area.x)); + sprintf(buf, "match/%s/%s/desk_area/y", b->client.name, b->client.class); + b->client.matched.desk_area.matched = e_db_int_get(db, buf, &(b->client.matched.desk_area.y)); + sprintf(buf, "match/%s/%s/size/w", b->client.name, b->client.class); + b->client.matched.size.matched = e_db_int_get(db, buf, &(b->client.matched.size.w)); + sprintf(buf, "match/%s/%s/size/h", b->client.name, b->client.class); + b->client.matched.size.matched = e_db_int_get(db, buf, &(b->client.matched.size.h)); + sprintf(buf, "match/%s/%s/desktop/desk", b->client.name, b->client.class); + b->client.matched.desktop.matched = e_db_int_get(db, buf, &(b->client.matched.desktop.desk)); + sprintf(buf, "match/%s/%s/sticky/sticky", b->client.name, b->client.class); + b->client.matched.sticky.matched = e_db_int_get(db, buf, &(b->client.matched.sticky.sticky)); + sprintf(buf, "match/%s/%s/layer/layer", b->client.name, b->client.class); + b->client.matched.layer.matched = e_db_int_get(db, buf, &(b->client.matched.layer.layer)); + + if (b->client.matched.prog_location.matched) + { + b->client.pos.requested = 0; + } + if (b->client.matched.border.matched) + { + IF_FREE(b->border_style); + b->border_style = b->client.matched.border.style; + } + if (b->client.matched.location.matched) + { + b->client.pos.requested = 1; + b->client.pos.gravity = NorthWestGravity; + b->client.pos.x = b->client.matched.location.x; + b->client.pos.y = b->client.matched.location.y; + b->client.no_place = 1; + } + if (b->client.matched.desk_area.matched) + { + b->client.pos.x += (b->client.matched.desk_area.x - b->desk->desk.area.x) * b->desk->real.w; + b->client.pos.y += (b->client.matched.desk_area.y - b->desk->desk.area.y) * b->desk->real.h; + b->client.area.x = b->client.matched.desk_area.x; + b->client.area.y = b->client.matched.desk_area.y; + } + if (b->client.matched.size.matched) + { + b->current.requested.w = b->client.matched.size.w; + b->current.requested.h = b->client.matched.size.h; + ecore_window_resize(b->win.client, b->client.matched.size.w, b->client.matched.size.h); + } + if (b->client.matched.desktop.matched) + { + b->client.desk = b->client.matched.desktop.desk; + e_border_raise(b); + if (b->client.desk != b->desk->desk.desk) b->current.requested.visible = 0; + b->client.no_place = 1; + } + if (b->client.matched.sticky.matched) + { + b->client.sticky = b->client.matched.sticky.sticky; + } + if (b->client.matched.layer.matched) + { + b->client.layer = b->client.matched.layer.layer; + } + e_db_close(db); + + D_RETURN; +} + +void +e_match_save_props(E_Border *b) +{ + char buf[PATH_MAX]; + E_DB_File *db; + + D_ENTER; + + db = e_db_open(e_config_get("match")); + if (!db) D_RETURN; + + sprintf(buf, "match/%s/%s/match", b->client.name, b->client.class); + e_db_int_set(db, buf, b->client.matched.matched); + + if (b->client.matched.location.matched) + { + printf("write location %i %i\n", b->current.x, b->current.y); + b->client.matched.location.x = b->current.x; + b->client.matched.location.y = b->current.y; + sprintf(buf, "match/%s/%s/location/x", b->client.name, b->client.class); + e_db_int_set(db, buf, b->client.matched.location.x); + sprintf(buf, "match/%s/%s/location/y", b->client.name, b->client.class); + e_db_int_set(db, buf, b->client.matched.location.y); + } + else + { + sprintf(buf, "match/%s/%s/location/x", b->client.name, b->client.class); + e_db_data_del(db, buf); + sprintf(buf, "match/%s/%s/location/y", b->client.name, b->client.class); + e_db_data_del(db, buf); + } + e_db_close(db); + e_db_flush(); D_RETURN; } diff --git a/src/match.h b/src/match.h index b9e814632..301407631 100644 --- a/src/match.h +++ b/src/match.h @@ -3,8 +3,10 @@ #include "e.h" #include "border.h" +#include "desktops.h" void e_match_set_props(E_Border *b); +void e_match_save_props(E_Border *b); #endif diff --git a/tools/e_setup.c b/tools/e_setup.c index 5e0a8bec7..499ead365 100644 --- a/tools/e_setup.c +++ b/tools/e_setup.c @@ -589,6 +589,15 @@ e_file_list_dir(char *dir) return list; } +void +e_file_list_dir_free(Evas_List list) +{ + while (list) + { + FREE(list->data); + list = evas_list_remove(list, list->data); + } +} /* */ /* */ @@ -627,6 +636,7 @@ void mouse_move(Ecore_Event * ev); void mouse_down(Ecore_Event * ev); void mouse_up(Ecore_Event * ev); void key_down(Ecore_Event * ev); +void child_exit(Ecore_Event *ev); void setup(void); Text_Zone *txz_new(double x, double y, char *text); void txz_free(Text_Zone *txz); @@ -634,6 +644,7 @@ void txz_show(Text_Zone *txz); void txz_hide(Text_Zone *txz); void txz_move(Text_Zone *txz, double x, double y); void txz_text(Text_Zone *txz, char *text); +void txz_adjust_txt(Text_Zone *txz); void animate_logo(int v, void *data); void @@ -693,6 +704,18 @@ key_down(Ecore_Event * ev) } } +void +child_exit(Ecore_Event *ev) +{ + Ecore_Event_Child *e; + + e = ev->event; +/* + e->pid; + e->exit_code; + */ +} + void setup(void) { @@ -704,6 +727,7 @@ setup(void) ecore_event_filter_handler_add(ECORE_EVENT_MOUSE_DOWN, mouse_down); ecore_event_filter_handler_add(ECORE_EVENT_MOUSE_UP, mouse_up); ecore_event_filter_handler_add(ECORE_EVENT_KEY_DOWN, key_down); + ecore_event_filter_handler_add(ECORE_EVENT_CHILD, child_exit); ecore_event_filter_idle_handler_add(idle, NULL); @@ -973,34 +997,6 @@ _txz_cb_title_move(void *_data, Ebits_Object _o, } } -void -txz_adjust_txt(Text_Zone *txz) -{ - Evas_List l; - double ypos; - - ypos = txz->l.y + 4; - evas_move(evas, txz->clip, txz->l.x, txz->l.y); - evas_resize(evas, txz->clip, txz->l.w, txz->l.h); - for (l = txz->lines; l; l = l->next) - { - Evas_Object o; - double tw, th; - double x; - char align; - - o = l->data; - align = (char)evas_get_data(evas, o, "align"); - x = txz->l.x + 4; - tw = evas_get_text_width(evas, o); - th = evas_get_text_height(evas, o); - if (align == 'c') x = txz->l.x + 4 + ((txz->l.w - 8 - tw) / 2); - else if (align == 'r') x = txz->l.x + 4 + (txz->l.w - 8 - tw); - evas_move(evas, o, x, ypos); - ypos += th; - } -} - Text_Zone * txz_new(double x, double y, char *text) { @@ -1146,7 +1142,7 @@ txz_text(Text_Zone *txz, char *text) else evas_move(evas, o, txz->x + ((512 - tw) / 2), ypos); evas_set_clip(evas, o, txz->clip); - evas_put_data(evas, o, "align", (void *)align[0]); + evas_put_data(evas, o, "align", (void *)((int)align[0])); ypos += th; p = tok + 1; @@ -1164,6 +1160,34 @@ txz_text(Text_Zone *txz, char *text) } } +void +txz_adjust_txt(Text_Zone *txz) +{ + Evas_List l; + double ypos; + + ypos = txz->l.y + 4; + evas_move(evas, txz->clip, txz->l.x, txz->l.y); + evas_resize(evas, txz->clip, txz->l.w, txz->l.h); + for (l = txz->lines; l; l = l->next) + { + Evas_Object o; + double tw, th; + double x; + char align; + + o = l->data; + align = (char)((int)evas_get_data(evas, o, "align")); + x = txz->l.x + 4; + tw = evas_get_text_width(evas, o); + th = evas_get_text_height(evas, o); + if (align == 'c') x = txz->l.x + 4 + ((txz->l.w - 8 - tw) / 2); + else if (align == 'r') x = txz->l.x + 4 + (txz->l.w - 8 - tw); + evas_move(evas, o, x, ypos); + ypos += th; + } +} + void animate_logo(int v, void *data) {