LineBuf.set_attribute
This commit is contained in:
parent
e3fdd3089d
commit
7687e75de4
@ -37,6 +37,11 @@ PyInit_fast_data_types(void) {
|
||||
if (!init_Line(m)) return NULL;
|
||||
if (!init_Cursor(m)) return NULL;
|
||||
if (!add_module_gl_constants(m)) return NULL;
|
||||
PyModule_AddIntConstant(m, "BOLD", BOLD_SHIFT);
|
||||
PyModule_AddIntConstant(m, "ITALIC", ITALIC_SHIFT);
|
||||
PyModule_AddIntConstant(m, "REVERSE", REVERSE_SHIFT);
|
||||
PyModule_AddIntConstant(m, "STRIKETHROUGH", STRIKE_SHIFT);
|
||||
PyModule_AddIntConstant(m, "DECORATION", DECORATION_SHIFT);
|
||||
}
|
||||
|
||||
return m;
|
||||
|
||||
@ -44,6 +44,12 @@ typedef unsigned int index_type;
|
||||
c->decoration = (a >> DECORATION_SHIFT) & 3; c->bold = (a >> BOLD_SHIFT) & 1; c->italic = (a >> ITALIC_SHIFT) & 1; \
|
||||
c->reverse = (a >> REVERSE_SHIFT) & 1; c->strikethrough = (a >> STRIKE_SHIFT) & 1;
|
||||
|
||||
#define SET_ATTRIBUTE(chars, shift, val) \
|
||||
mask = shift == DECORATION_SHIFT ? 3 : 1; \
|
||||
val = (val & mask) << (ATTRS_SHIFT + shift); \
|
||||
mask = ~(mask << (ATTRS_SHIFT + shift)); \
|
||||
for (index_type i = 0; i < self->xnum; i++) (chars)[i] = ((chars)[i] & mask) | val;
|
||||
|
||||
#define COPY_CELL(src, s, dest, d) \
|
||||
(dest)->chars[d] = (self)->chars[s]; \
|
||||
(dest)->colors[d] = (self)->colors[s]; \
|
||||
|
||||
@ -101,6 +101,19 @@ line(LineBuf *self, PyObject *y) {
|
||||
return (PyObject*)self->line;
|
||||
}
|
||||
|
||||
static PyObject*
|
||||
set_attribute(LineBuf *self, PyObject *args) {
|
||||
#define set_attribute_doc "set_attribute(which, val) -> Set the attribute on all cells in the line."
|
||||
unsigned int shift, val;
|
||||
char_type mask;
|
||||
if (!PyArg_ParseTuple(args, "II", &shift, &val)) return NULL;
|
||||
if (shift < DECORATION_SHIFT || shift > STRIKE_SHIFT) { PyErr_SetString(PyExc_ValueError, "Unknown attribute"); return NULL; }
|
||||
for (index_type y = 0; y < self->ynum; y++) {
|
||||
SET_ATTRIBUTE(self->chars + y * self->xnum, shift, val);
|
||||
}
|
||||
Py_RETURN_NONE;
|
||||
}
|
||||
|
||||
|
||||
// Boilerplate {{{
|
||||
static PyObject*
|
||||
@ -111,6 +124,7 @@ static PyMethodDef methods[] = {
|
||||
METHOD(line, METH_O)
|
||||
METHOD(copy_old, METH_O)
|
||||
METHOD(clear, METH_NOARGS)
|
||||
METHOD(set_attribute, METH_VARARGS)
|
||||
{NULL, NULL, 0, NULL} /* Sentinel */
|
||||
};
|
||||
|
||||
|
||||
12
kitty/line.c
12
kitty/line.c
@ -245,6 +245,17 @@ set_char(Line *self, PyObject *args) {
|
||||
Py_RETURN_NONE;
|
||||
}
|
||||
|
||||
static PyObject*
|
||||
set_attribute(Line *self, PyObject *args) {
|
||||
#define set_attribute_doc "set_attribute(which, val) -> Set the attribute on all cells in the line."
|
||||
unsigned int shift, val;
|
||||
char_type mask;
|
||||
if (!PyArg_ParseTuple(args, "II", &shift, &val)) return NULL;
|
||||
if (shift < DECORATION_SHIFT || shift > STRIKE_SHIFT) { PyErr_SetString(PyExc_ValueError, "Unknown attribute"); return NULL; }
|
||||
SET_ATTRIBUTE(self->chars, shift, val);
|
||||
Py_RETURN_NONE;
|
||||
}
|
||||
|
||||
static Py_ssize_t
|
||||
__len__(PyObject *self) {
|
||||
return (Py_ssize_t)(((Line*)self)->ynum);
|
||||
@ -281,6 +292,7 @@ static PyMethodDef methods[] = {
|
||||
METHOD(right_shift, METH_VARARGS)
|
||||
METHOD(left_shift, METH_VARARGS)
|
||||
METHOD(set_char, METH_VARARGS)
|
||||
METHOD(set_attribute, METH_VARARGS)
|
||||
|
||||
{NULL} /* Sentinel */
|
||||
};
|
||||
|
||||
@ -12,7 +12,7 @@ from pyte import charsets as cs, graphics as g, modes as mo
|
||||
from .data_types import Line, Cursor, rewrap_lines
|
||||
from .utils import wcwidth, is_simple_string, sanitize_title
|
||||
from .unicode import ignore_pat
|
||||
from .fast_data_types import LineBuf
|
||||
from .fast_data_types import LineBuf, REVERSE
|
||||
|
||||
|
||||
#: A container for screen's scroll margins.
|
||||
@ -79,7 +79,7 @@ class Screen:
|
||||
self.tophistorybuf.copy_old(previous)
|
||||
|
||||
def line(self, i):
|
||||
return self.linebuf[i]
|
||||
return self.linebuf.line(i)
|
||||
|
||||
def __repr__(self):
|
||||
return ("{0}({1}, {2})".format(self.__class__.__name__,
|
||||
@ -121,7 +121,6 @@ class Screen:
|
||||
if self.linebuf is self.alt_linebuf:
|
||||
self.toggle_screen_buffer()
|
||||
self.linebuf.clear()
|
||||
self.linebuf[:] = (Line(self.columns) for i in range(self.lines))
|
||||
self.mode = {mo.DECAWM, mo.DECTCEM}
|
||||
self.margins = Margins(0, self.lines - 1)
|
||||
|
||||
@ -236,9 +235,7 @@ class Screen:
|
||||
|
||||
# Mark all displayed characters as reverse.
|
||||
if mo.DECSCNM in modes:
|
||||
for line in self.linebuf:
|
||||
for i in range(len(line)):
|
||||
line.set_reverse(i, True)
|
||||
self.linebuf.set_attribute(REVERSE, True)
|
||||
self.update_screen()
|
||||
self.select_graphic_rendition(7) # +reverse.
|
||||
|
||||
@ -282,9 +279,7 @@ class Screen:
|
||||
self.cursor_position()
|
||||
|
||||
if mo.DECSCNM in modes:
|
||||
for line in self.linebuf:
|
||||
for i in range(len(line)):
|
||||
line.set_reverse(i, False)
|
||||
self.linebuf.set_attribute(REVERSE, False)
|
||||
self.update_screen()
|
||||
self.select_graphic_rendition(27) # -reverse.
|
||||
|
||||
|
||||
@ -7,7 +7,7 @@ import codecs
|
||||
from . import BaseTest, filled_line_buf, filled_cursor
|
||||
|
||||
from kitty.utils import is_simple_string, wcwidth, sanitize_title
|
||||
from kitty.fast_data_types import LineBuf, Cursor as C
|
||||
from kitty.fast_data_types import LineBuf, Cursor as C, REVERSE
|
||||
|
||||
|
||||
class TestDataTypes(BaseTest):
|
||||
@ -19,6 +19,12 @@ class TestDataTypes(BaseTest):
|
||||
self.ae(new.line(0), old.line(1))
|
||||
new.clear()
|
||||
self.ae(str(new.line(0)), ' ' * new.xnum)
|
||||
old.set_attribute(REVERSE, False)
|
||||
for y in range(old.ynum):
|
||||
for x in range(old.xnum):
|
||||
c = old.line(y).cursor_from(x)
|
||||
self.assertFalse(c.reverse)
|
||||
self.assertTrue(c.bold)
|
||||
|
||||
def test_line(self):
|
||||
lb = LineBuf(2, 3)
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user