Refactor screen mode API to use get/setters

This commit is contained in:
Kovid Goyal 2017-01-04 10:24:00 +05:30
parent b4af2ff314
commit af8d44ecab
6 changed files with 36 additions and 17 deletions

View File

@ -278,7 +278,7 @@ class Boss(Thread):
passthrough = f() passthrough = f()
if not passthrough: if not passthrough:
return return
if window.screen.auto_repeat_enabled() or action == GLFW_PRESS: if window.screen.auto_repeat_enabled or action == GLFW_PRESS:
if window.char_grid.scrolled_by and key not in MODIFIER_KEYS: if window.char_grid.scrolled_by and key not in MODIFIER_KEYS:
window.scroll_end() window.scroll_end()
data = interpret_key_event(key, scancode, mods) data = interpret_key_event(key, scancode, mods)

View File

@ -447,7 +447,7 @@ class CharGrid:
def render_cursor(self, sg, cursor_program): def render_cursor(self, sg, cursor_program):
cursor = self.current_cursor cursor = self.current_cursor
if self.screen.cursor_hidden() or self.scrolled_by: if not self.screen.cursor_visible or self.scrolled_by:
return return
def width(w=2, vert=True): def width(w=2, vert=True):

View File

@ -1025,12 +1025,14 @@ WRAP1E(cursor_back, 1, -1)
WRAP1B(erase_in_line, 0) WRAP1B(erase_in_line, 0)
WRAP1B(erase_in_display, 0) WRAP1B(erase_in_display, 0)
#define MODE_GETTER(name, uname) \ #define MODE_GETSET(name, uname) \
static PyObject* name(Screen *self) { PyObject *ans = self->modes.m##uname ? Py_True : Py_False; Py_INCREF(ans); return ans; } static PyObject* name##_get(Screen *self, void UNUSED *closure) { PyObject *ans = self->modes.m##uname ? Py_True : Py_False; Py_INCREF(ans); return ans; } \
static int name##_set(Screen *self, PyObject *val, void UNUSED *closure) { if (val == NULL) { PyErr_SetString(PyExc_TypeError, "Cannot delete attribute"); return -1; } set_mode_from_const(self, uname, PyObject_IsTrue(val) ? true : false); return 0; }
MODE_GETTER(in_bracketed_paste_mode, BRACKETED_PASTE) MODE_GETSET(in_bracketed_paste_mode, BRACKETED_PASTE)
MODE_GETTER(focus_tracking_enabled, FOCUS_TRACKING) MODE_GETSET(focus_tracking_enabled, FOCUS_TRACKING)
MODE_GETTER(auto_repeat_enabled, DECARM) MODE_GETSET(auto_repeat_enabled, DECARM)
MODE_GETSET(cursor_visible, DECTCEM)
static PyObject* static PyObject*
mouse_tracking_mode(Screen *self) { mouse_tracking_mode(Screen *self) {
@ -1160,10 +1162,9 @@ is_main_linebuf(Screen *self) {
} }
static PyObject* static PyObject*
cursor_hidden(Screen *self) { toggle_alt_screen(Screen *self) {
PyObject *ret = self->modes.mDECTCEM ? Py_False : Py_True; screen_toggle_screen_buffer(self);
Py_INCREF(ret); Py_RETURN_NONE;
return ret;
} }
WRAP2(cursor_position, 1, 1) WRAP2(cursor_position, 1, 1)
@ -1180,6 +1181,7 @@ COUNT_WRAP(cursor_down1)
COUNT_WRAP(cursor_forward) COUNT_WRAP(cursor_forward)
#define MND(name, args) {#name, (PyCFunction)name, args, #name}, #define MND(name, args) {#name, (PyCFunction)name, args, #name},
#define MODEFUNC(name) MND(name, METH_NOARGS) MND(set_##name, METH_O)
static PyMethodDef methods[] = { static PyMethodDef methods[] = {
MND(line, METH_O) MND(line, METH_O)
@ -1202,7 +1204,6 @@ static PyMethodDef methods[] = {
MND(change_scrollback_size, METH_VARARGS) MND(change_scrollback_size, METH_VARARGS)
MND(erase_characters, METH_VARARGS) MND(erase_characters, METH_VARARGS)
MND(cursor_up, METH_VARARGS) MND(cursor_up, METH_VARARGS)
MND(cursor_hidden, METH_NOARGS)
MND(mouse_tracking_mode, METH_NOARGS) MND(mouse_tracking_mode, METH_NOARGS)
MND(mouse_tracking_protocol, METH_NOARGS) MND(mouse_tracking_protocol, METH_NOARGS)
MND(cursor_up1, METH_VARARGS) MND(cursor_up1, METH_VARARGS)
@ -1223,15 +1224,21 @@ static PyMethodDef methods[] = {
MND(set_margins, METH_VARARGS) MND(set_margins, METH_VARARGS)
MND(set_scroll_cell_data, METH_VARARGS) MND(set_scroll_cell_data, METH_VARARGS)
MND(apply_selection, METH_VARARGS) MND(apply_selection, METH_VARARGS)
MND(in_bracketed_paste_mode, METH_NOARGS) MND(toggle_alt_screen, METH_NOARGS)
MND(auto_repeat_enabled, METH_NOARGS)
MND(focus_tracking_enabled, METH_NOARGS)
{"update_cell_data", (PyCFunction)screen_update_cell_data, METH_VARARGS, ""}, {"update_cell_data", (PyCFunction)screen_update_cell_data, METH_VARARGS, ""},
{"select_graphic_rendition", (PyCFunction)_select_graphic_rendition, METH_VARARGS, ""}, {"select_graphic_rendition", (PyCFunction)_select_graphic_rendition, METH_VARARGS, ""},
{NULL} /* Sentinel */ {NULL} /* Sentinel */
}; };
static PyGetSetDef getsetters[] = {
GETSET(in_bracketed_paste_mode)
GETSET(auto_repeat_enabled)
GETSET(focus_tracking_enabled)
GETSET(cursor_visible)
{NULL} /* Sentinel */
};
static PyMemberDef members[] = { static PyMemberDef members[] = {
{"callbacks", T_OBJECT_EX, offsetof(Screen, callbacks), 0, "callbacks"}, {"callbacks", T_OBJECT_EX, offsetof(Screen, callbacks), 0, "callbacks"},
{"cursor", T_OBJECT_EX, offsetof(Screen, cursor), READONLY, "cursor"}, {"cursor", T_OBJECT_EX, offsetof(Screen, cursor), READONLY, "cursor"},
@ -1254,6 +1261,7 @@ PyTypeObject Screen_Type = {
.tp_methods = methods, .tp_methods = methods,
.tp_members = members, .tp_members = members,
.tp_new = new, .tp_new = new,
.tp_getset = getsetters,
}; };
INIT_TYPE(Screen) INIT_TYPE(Screen)

View File

@ -111,10 +111,10 @@ class Window:
def focus_changed(self, focused): def focus_changed(self, focused):
if focused: if focused:
if self.screen.focus_tracking_enabled(): if self.screen.focus_tracking_enabled:
self.write_to_child(b'\x1b[I') self.write_to_child(b'\x1b[I')
else: else:
if self.screen.focus_tracking_enabled(): if self.screen.focus_tracking_enabled:
self.write_to_child(b'\x1b[O') self.write_to_child(b'\x1b[O')
def title_changed(self, new_title): def title_changed(self, new_title):

View File

@ -30,9 +30,13 @@ class Callbacks:
def request_capabilities(self, q): def request_capabilities(self, q):
self.qbuf += q self.qbuf += q
def buf_toggled(self, is_alt):
self.is_alt = is_alt
def clear(self): def clear(self):
self.wtcbuf = b'' self.wtcbuf = b''
self.iconbuf = self.titlebuf = self.colorbuf = self.qbuf = self.ctbuf = '' self.iconbuf = self.titlebuf = self.colorbuf = self.qbuf = self.ctbuf = ''
self.is_alt = False
def filled_line_buf(ynum=5, xnum=5, cursor=Cursor()): def filled_line_buf(ynum=5, xnum=5, cursor=Cursor()):

View File

@ -332,3 +332,10 @@ class TestScreen(BaseTest):
c = s.line(1).cursor_from(0) c = s.line(1).cursor_from(0)
self.ae(c.fg, (5 << 8) | 1) self.ae(c.fg, (5 << 8) | 1)
self.ae(c.bg, 0) self.ae(c.bg, 0)
def test_cursor_hidden(self):
s = self.create_screen()
s.toggle_alt_screen()
s.cursor_visible = False
s.toggle_alt_screen()
self.assertFalse(s.cursor_visible)