diff options
| author | ruki <[email protected]> | 2017-12-16 00:57:23 +0800 |
|---|---|---|
| committer | ruki <[email protected]> | 2017-12-15 23:44:19 +0800 |
| commit | e5ed897840214b66fd746292fff15c56606d3251 (patch) | |
| tree | 6a5820bfcb1acf95536b673cd79587aff198dab5 /xmake/core/ui/program.lua | |
| parent | d81f894af27987981ef3fe39e013ad3f1fadfbcf (diff) | |
add event to ui
Diffstat (limited to 'xmake/core/ui/program.lua')
| -rw-r--r-- | xmake/core/ui/program.lua | 154 |
1 files changed, 154 insertions, 0 deletions
diff --git a/xmake/core/ui/program.lua b/xmake/core/ui/program.lua index 75c08fc79..af3cb09bf 100644 --- a/xmake/core/ui/program.lua +++ b/xmake/core/ui/program.lua @@ -30,6 +30,7 @@ $Id: program.lua 18 2007-06-21 20:43:52Z tngd $ -- load modules local rect = require("ui/rect") local group = require("ui/group") +local event = require("ui/event") local curses = require("ui/curses") -- define module @@ -118,6 +119,28 @@ function program:argv() return self._ARGV end +-- get the current event +function program:event() + + -- get input key + local key_code, key_name, key_meta = self:_input_key() + if key_code then + if key_name == "Resize" or key_name == "CtrlL" then + self:change_bounds(Rect{0, 0, curses.columns(), curses.lines()}) + self:refresh() + elseif key_name == "Refresh" then + self:refresh() + else + return event.keyboard{key_code, key_name, key_meta} + end + end +end + +-- put an event to view +function program:event_put(e) + -- TODO +end + -- run program loop function program:loop(argv) @@ -128,5 +151,136 @@ function program:loop(argv) self:execute() end +-- get key map +function program:_key_map() + if not self._KEYMAP then + self._KEYMAP = + { + [ 1] = "CtrlA", [ 2] = "CtrlB", [ 3] = "CtrlC", + [ 4] = "CtrlD", [ 5] = "CtrlE", [ 6] = "CtrlF", + [ 7] = "CtrlG", [ 8] = "CtrlH", [ 9] = "CtrlI", + [10] = "CtrlJ", [11] = "CtrlK", [12] = "CtrlL", + [13] = "CtrlM", [14] = "CtrlN", [15] = "CtrlO", + [16] = "CtrlP", [17] = "CtrlQ", [18] = "CtrlR", + [19] = "CtrlS", [20] = "CtrlT", [21] = "CtrlU", + [22] = "CtrlV", [23] = "CtrlW", [24] = "CtrlX", + [25] = "CtrlY", [26] = "CtrlZ", + + [ 8] = "Backspace", + [ 9] = "Tab", + [ 10] = "Enter", + [ 13] = "Enter", + [ 27] = "Esc", + [ 31] = "CtrlBackspace", + [127] = "Backspace", + + [curses.KEY_DOWN ] = "Down", + [curses.KEY_UP ] = "Up", + [curses.KEY_LEFT ] = "Left", + [curses.KEY_RIGHT ] = "Right", + [curses.KEY_HOME ] = "Home", + [curses.KEY_END ] = "End", + [curses.KEY_NPAGE ] = "PageDown", + [curses.KEY_PPAGE ] = "PageUp", + [curses.KEY_IC ] = "Insert", + [curses.KEY_DC ] = "Delete", + [curses.KEY_BACKSPACE ] = "Backspace", + [curses.KEY_F1 ] = "F1", + [curses.KEY_F2 ] = "F2", + [curses.KEY_F3 ] = "F3", + [curses.KEY_F4 ] = "F4", + [curses.KEY_F5 ] = "F5", + [curses.KEY_F6 ] = "F6", + [curses.KEY_F7 ] = "F7", + [curses.KEY_F8 ] = "F8", + [curses.KEY_F9 ] = "F9", + [curses.KEY_F10 ] = "F10", + [curses.KEY_F11 ] = "F11", + [curses.KEY_F12 ] = "F12", + + [curses.KEY_RESIZE ] = "Resize", + [curses.KEY_REFRESH ] = "Refresh", + + [curses.KEY_BTAB ] = "ShiftTab", + [curses.KEY_SDC ] = "ShiftDelete", + [curses.KEY_SIC ] = "ShiftInsert", + [curses.KEY_SEND ] = "ShiftEnd", + [curses.KEY_SHOME ] = "ShiftHome", + [curses.KEY_SLEFT ] = "ShiftLeft", + [curses.KEY_SRIGHT ] = "ShiftRight", + } + end + return self._KEYMAP +end + +-- get input key +function program:_input_key() + + -- get main window + local main_window = self:main_window() + + -- get input character + local ch = main_window:getch() + if not ch then + return + end + + -- this is the time limit in ms within Esc-key sequences are detected as + -- Alt-letter sequences. useful when we can't generate Alt-letter sequences + -- directly. sometimes this pause may be longer than expected since the + -- curses driver may also pause waiting for another key (ncurses-5.3) + local esc_delay = 400 + + -- get key map + local key_map = self:_key_map() + + -- is alt? + local alt = ch == 27 + if alt then + + -- get the next input character + ch = main_window:getch() + if not ch then + + -- since there is no way to know the time with millisecond precision + -- we pause the the program until we get a key or the time limit + -- is reached + local t = 0 + while true do + ch = main_window:getch() + if ch or t >= esc_delay then + break + end + + -- wait some time, 50ms + curses.napms(50) + t = t + 50 + end + + -- nothing was typed... return Esc + if not ch then + return 27, "Esc", false + end + end + if ch > 96 and ch < 123 then + ch = ch - 32 + end + end + + -- map character to key + local key = key_map[ch] + local key_name = nil + if key then + key_name = alt and "Alt".. key or key + elseif (ch < 256) then + key_name = alt and "Alt".. string.char(ch) or string.char(ch) + else + return ch, '(noname)', alt + end + + -- return key info + return ch, key_name, alt +end + -- return module return program |
