From: NeilBrown Date: Thu, 3 Dec 2015 21:51:06 +0000 (+1100) Subject: separate keyboard-input state into separate module. X-Git-Tag: lca2016~127 X-Git-Url: http://git.neil.brown.name/?a=commitdiff_plain;h=0760c5a0e9afa1d93165ae3466ce1cc4859bf227;p=edlib.git separate keyboard-input state into separate module. This localises the concept and makes it possible to access the state by sending commands. Signed-off-by: NeilBrown --- diff --git a/Makefile b/Makefile index 366e263a..2256abca 100644 --- a/Makefile +++ b/Makefile @@ -16,7 +16,7 @@ SHOBJ = O/doc-text.o O/doc-dir.o \ O/render-hex.o O/render-lines.o \ O/render-format.o O/render-complete.o \ O/lib-view.o O/lib-tile.o O/lib-popup.o O/lib-line-count.o O/lib-keymap.o \ - O/lib-search.o O/lib-messageline.o \ + O/lib-search.o O/lib-messageline.o O/lib-input.o \ O/lang-python.o \ O/mode-emacs.o \ O/display-ncurses.o diff --git a/core-pane.c b/core-pane.c index c91fd5b5..3b61898c 100644 --- a/core-pane.c +++ b/core-pane.c @@ -407,40 +407,17 @@ struct pane *render_attach(char *name, struct pane *parent) void pane_set_mode(struct pane *p, char *mode, int transient) { - struct display *dd; - - if (!p->parent) - return; - while (p->parent->parent) - p = p->parent; - dd = p->data; - dd->mode = mode; - if (!transient) - dd->next_mode = mode; + call5("Mode:set-mode", p, 0, NULL, mode, !transient); } void pane_set_numeric(struct pane *p, int numeric) { - struct display *dd; - - if (!p->parent) - return; - while (p->parent->parent) - p = p->parent; - dd = p->data; - dd->numeric = numeric; + call3("Mode:set-numeric", p, numeric, NULL); } void pane_set_extra(struct pane *p, int extra) { - struct display *dd; - - if (!p->parent) - return; - while (p->parent->parent) - p = p->parent; - dd = p->data; - dd->extra = extra; + call5("Mode:set-extra", p, 0, NULL, NULL, extra); } struct pane *pane_attach(struct pane *p, char *type, struct pane *dp, diff --git a/core.h b/core.h index 849dc3be..c5b10d9a 100644 --- a/core.h +++ b/core.h @@ -6,7 +6,6 @@ * documents * marks and points * attributes - * displays * panes * keymaps * commands @@ -23,7 +22,6 @@ typedef _Bool bool; struct doc; struct mark; struct attrset; -struct display; struct pane; struct command; struct cmd_info; @@ -39,9 +37,8 @@ struct doc_ref { * This captures and documents the global states, and allows * multiple "editors" in the one process, should that be valuable. * - * Each document and each display contains a reference to the editor. - * The root pane of a pane tree must have a display as the 'data', which allows - * the editor to be found from any pane or point. + * Each document and contains a reference to the editor which is the root of the + * pane tree. */ struct pane { struct pane *parent; @@ -74,11 +71,6 @@ struct doc_data { struct mark *point; }; -struct display { - char *mode, *next_mode; - int numeric, extra; -}; - struct editor { struct pane root; struct event_base *base; @@ -306,7 +298,7 @@ struct command *key_register_prefix(char *name); enum { DAMAGED_CHILD = 1, - DAMAGED_SIZE = 2, /* these the each impose the next. */ + DAMAGED_SIZE = 2, /* these three each impose the next. */ DAMAGED_CONTENT = 4, DAMAGED_CURSOR = 8, }; diff --git a/display-ncurses.c b/display-ncurses.c index 98cae24c..07446ab9 100644 --- a/display-ncurses.c +++ b/display-ncurses.c @@ -27,7 +27,6 @@ #include "core.h" struct display_data { - struct display dpy; SCREEN *scr; }; @@ -189,10 +188,6 @@ static struct pane *ncurses_init(struct editor *ed) mousemask(ALL_MOUSE_EVENTS, NULL); dd->scr = NULL; - dd->dpy.mode = ""; - dd->dpy.next_mode = ""; - dd->dpy.numeric = NO_NUMERIC; - dd->dpy.extra = 0; current_screen = NULL; p = pane_register(&ed->root, 0, &ncurses_handle, dd, NULL); @@ -205,7 +200,7 @@ static struct pane *ncurses_init(struct editor *ed) handle_winch, p); event_add(l, NULL); pane_damaged(p, DAMAGED_SIZE); - return p; + return pane_attach(p, "input", NULL, NULL); } static void handle_winch(int sig, short ev, void *vpane) @@ -324,55 +319,38 @@ static char *find_name (struct namelist *l, wint_t c) static void send_key(int keytype, wint_t c, struct pane *p) { - struct display_data *dd = p->data; - struct cmd_info ci = {0}; - char *k, *n; + char *n; char buf[100];/* FIXME */ - strcpy(buf, dd->dpy.mode); - k = buf + strlen(buf); if (keytype == KEY_CODE_YES) { n = find_name(key_names, c); if (!n) - sprintf(k, "Ncurs-%o", c); + sprintf(buf, "Ncurs-%o", c); else - strcpy(k, n); + strcpy(buf, n); } else { n = find_name(char_names, c); if (n) - strcpy(k, n); + strcpy(buf, n); else if (c < ' ') - sprintf(k, "C-Chr-%c", c+64); + sprintf(buf, "C-Chr-%c", c+64); else - sprintf(k, "Chr-%lc", c); + sprintf(buf, "Chr-%lc", c); } - ci.key = buf; - ci.focus = p; - ci.numeric = dd->dpy.numeric; - ci.extra = dd->dpy.extra; - dd->dpy.mode = dd->dpy.next_mode; - dd->dpy.numeric = NO_NUMERIC; - dd->dpy.extra = 0; - key_handle_focus_point(&ci); + call5("Keystroke", p, 0, NULL, buf, 0); } static void do_send_mouse(struct pane *p, int x, int y, char *cmd) { - struct display_data *dd = p->data; struct cmd_info ci = {0}; - char buf[100];/* FIXME */ - ci.key = strcat(strcpy(buf, dd->dpy.mode), cmd); + ci.key = "Mouse-event"; + ci.str = cmd; ci.focus = p; - ci.numeric = dd->dpy.numeric; - ci.extra = dd->dpy.extra; ci.x = x; ci.y = y; - dd->dpy.mode = dd->dpy.next_mode; - dd->dpy.numeric = NO_NUMERIC; - dd->dpy.extra = 0; - key_handle_xy_point(&ci); + key_handle_xy(&ci); } static void send_mouse(MEVENT *mev, struct pane *p) diff --git a/edlib.c b/edlib.c index cd8d79da..6882ba96 100644 --- a/edlib.c +++ b/edlib.c @@ -84,9 +84,9 @@ int main(int argc, char *argv[]) ci.str = "python/test.py"; key_lookup(ed->commands, &ci); - pane_refresh(root); + pane_refresh(&ed->root); event_base_dispatch(base); } - pane_close(root); + pane_close(&ed->root); exit(0); } diff --git a/lib-input.c b/lib-input.c new file mode 100644 index 00000000..e09b578b --- /dev/null +++ b/lib-input.c @@ -0,0 +1,122 @@ +/* + * Copyright Neil Brown ©2015 + * May be distributed under terms of GPLv2 - see file:COPYING + * + * Core input translation. + * This module transalates keystrokes and mouse events into commands. + * This involves tracking the current 'mode' state. + * + */ + +#include +#include +#include + +#include "core.h" + +struct input_mode { + char *mode; + int numeric, extra; +}; + + +DEF_CMD(set_mode) +{ + struct input_mode *im = ci->home->data; + + im->mode = ci->str; + return 1; +} + +DEF_CMD(set_numeric) +{ + struct input_mode *im = ci->home->data; + + im->numeric = ci->numeric; + return 1; +} + +DEF_CMD(set_extra) +{ + struct input_mode *im = ci->home->data; + + im->extra = ci->extra; + return 1; +} + +DEF_CMD(keystroke) +{ + struct cmd_info ci2 = {0}; + struct input_mode *im = ci->home->data; + int l; + + l = strlen(im->mode) + strlen(ci->str) + 1; + ci2.key = malloc(l); + strcat(strcpy(ci2.key, im->mode), ci->str); + ci2.focus = ci->home; + ci2.numeric = im->numeric; + ci2.extra = im->extra; + + im->mode = ""; + im->numeric = NO_NUMERIC; + im->extra = 0; + key_handle_focus_point(&ci2); + free(ci2.key); + return 0; +} + +DEF_CMD(mouse_event) +{ + struct input_mode *im = ci->home->data; + int l; + struct cmd_info ci2 = {0}; + + l = strlen(im->mode) + strlen(ci->str) + 1; + ci2.key = malloc(l); + strcat(strcpy(ci2.key, im->mode), ci->str); + ci2.focus = ci->home; + ci2.numeric = im->numeric; + ci2.extra = im->extra; + ci2.x = ci->hx; + ci2.y = ci->hy; + + im->mode = ""; + im->numeric = NO_NUMERIC; + im->extra = 0; + + key_handle_xy_point(&ci2); + return 0; +} + +static struct map *im_map; +static void register_map(void) +{ + if (im_map) + return; + im_map = key_alloc(); + key_add(im_map, "Keystroke", &keystroke); + key_add(im_map, "Mouse-event", &mouse_event); + key_add(im_map, "Mode:set-mode", &set_mode); + key_add(im_map, "Mode:set-numeric", &set_numeric); + key_add(im_map, "Mode:set-extra", &set_extra); +} + +DEF_LOOKUP_CMD(input_handle, im_map); +DEF_CMD(input_attach) +{ + struct input_mode *im = malloc(sizeof(*im)); + + register_map(); + + im->mode = ""; + im->numeric = NO_NUMERIC; + im->extra = 0; + + ci->focus = pane_register(ci->focus, 0, &input_handle.c, im, NULL); + return 1; +} + +void edlib_init(struct editor *ed) +{ + key_add(ed->commands, "attach-input", &input_attach); +} diff --git a/lib-messageline.c b/lib-messageline.c index 5c1fdd82..9243cd30 100644 --- a/lib-messageline.c +++ b/lib-messageline.c @@ -64,7 +64,7 @@ DEF_CMD(messageline_handle) return 1; } /* Anything else clears the message */ - if (strncmp(ci->key, "pane", 4) != 0 && mli->message) { + if (strcmp(ci->key, "Keystroke") == 0 && mli->message) { free(mli->message); mli->message = NULL; pane_clear(mli->line, "");