I wrote a path set for stterm which adds handling of TBC and HTS sequences
(and logically of HT character). I also removed the comment:


XXX: (CSI n I) CHT -- Cursor Forward Tabulation <n> tab stops

because CHT is not a vt10x escape sequence, it is a vt51x sequence, and I
think this could mean adding non necessary stuff (I wrote the patch for this
sequence also, so if you want it, ask me for it). It is not implemented by
linux virtual terminal neither by xterm.

Roberto.
>From 057c24bb41e918224c1dc3d841015180ab56a7cb Mon Sep 17 00:00:00 2001
From: "Roberto E. Vargas Caballero" <k...@shike2.com>
Date: Wed, 15 Aug 2012 09:21:14 +0200
Subject: [PATCH 1/3] Add tabs field into Term struct

Tabs stop are simulated in st using a fixed size of 8, always, without be
worried about sequences changing the tab stops. A user can put a tab stop in
each horizontal position of the screen, so we need at least one flag for
each column of the screen. In the same way as dirty flags is used for the
rows, it is used a bool dinamic array.

Signed-off-by: Roberto E. Vargas Caballero <k...@shike2.com>
---
 st.c |   22 +++++++++++++++++++---
 1 file changed, 19 insertions(+), 3 deletions(-)

diff --git a/st.c b/st.c
index 4fc4d3d..d169ddf 100644
--- a/st.c
+++ b/st.c
@@ -164,7 +164,7 @@ typedef struct {
 	int col;	/* nb col */
 	Line* line;	/* screen */
 	Line* alt;	/* alternate screen */
-	bool* dirty; /* dirtyness of lines */
+	bool* dirty;	/* dirtyness of lines */
 	TCursor c;	/* cursor */
 	int top;	/* top    scroll limit */
 	int bot;	/* bottom scroll limit */
@@ -172,6 +172,7 @@ typedef struct {
 	int esc;	/* escape state flags */
 	char title[ESC_TITLE_SIZ];
 	int titlelen;
+	bool *tabs;
 } Term;
 
 /* Purely graphic info */
@@ -847,12 +848,16 @@ tcursor(int mode) {
 
 void
 treset(void) {
+	unsigned i;
 	term.c = (TCursor){{
 		.mode = ATTR_NULL,
 		.fg = DefaultFG,
 		.bg = DefaultBG
 	}, .x = 0, .y = 0, .state = CURSOR_DEFAULT};
-	
+
+	memset(term.tabs, 0, term.col * sizeof(*term.tabs));
+	for (i = TAB; i < term.col; i += TAB)
+		term.tabs[i] = 1;
 	term.top = 0, term.bot = term.row - 1;
 	term.mode = MODE_WRAP;
 	tclearregion(0, 0, term.col-1, term.row-1);
@@ -865,12 +870,14 @@ tnew(int col, int row) {
 	term.line = malloc(term.row * sizeof(Line));
 	term.alt  = malloc(term.row * sizeof(Line));
 	term.dirty = malloc(term.row * sizeof(*term.dirty));
+	term.tabs = malloc(term.col * sizeof(*term.tabs));
 
 	for(row = 0; row < term.row; row++) {
 		term.line[row] = malloc(term.col * sizeof(Glyph));
 		term.alt [row] = malloc(term.col * sizeof(Glyph));
 		term.dirty[row] = 0;
 	}
+	memset(term.tabs, 0, term.col * sizeof(*term.tabs));
 	/* setup screen */
 	treset();
 }
@@ -1588,6 +1595,7 @@ tresize(int col, int row) {
 	term.line = realloc(term.line, row * sizeof(Line));
 	term.alt  = realloc(term.alt,  row * sizeof(Line));
 	term.dirty = realloc(term.dirty, row * sizeof(*term.dirty));
+	term.tabs = realloc(term.tabs, col * sizeof(*term.tabs));
 
 	/* resize each row to new width, zero-pad if needed */
 	for(i = 0; i < minrow; i++) {
@@ -1606,7 +1614,15 @@ tresize(int col, int row) {
 		term.line[i] = calloc(col, sizeof(Glyph));
 		term.alt [i] = calloc(col, sizeof(Glyph));
 	}
-	
+	if (col > term.col) {
+		bool *bp = term.tabs + term.col;
+
+		memset(bp, 0, sizeof(*term.tabs) * (col - term.col));
+		while (--bp > term.tabs && !*bp)
+			/* nothing */ ;
+		for (bp += TAB; bp < term.tabs + col; bp += TAB)
+			*bp = 1;
+	}
 	/* update terminal size */
 	term.col = col, term.row = row;
 	/* make use of the LIMIT in tmoveto */
-- 
1.7.10.4

>From 1adde6a59379be80c47f6e02afcc2ffe26bec895 Mon Sep 17 00:00:00 2001
From: "Roberto E. Vargas Caballero" <k...@shike2.com>
Date: Wed, 15 Aug 2012 10:09:22 +0200
Subject: [PATCH 2/3] Add HTS sequence

This sequence adds a new tab stop in the current horizontal position. This
means that tputtab must be look for the next tab stop in the tabs array
instead of using a hard coded value offset. Also, CHT sequence XXX message
is removed because it is not a vt10x sequence (as far as I know it is a
vt50x sequence), and it is not implemented by linux virtual terminal neither
by xterm.

Signed-off-by: Roberto E. Vargas Caballero <k...@shike2.com>
---
 st.c |   12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/st.c b/st.c
index d169ddf..4b7e4eb 100644
--- a/st.c
+++ b/st.c
@@ -1214,7 +1214,6 @@ csihandle(void) {
 		DEFAULT(escseq.arg[1], 1);
 		tmoveto(escseq.arg[1]-1, escseq.arg[0]-1);
 		break;
-	/* XXX: (CSI n I) CHT -- Cursor Forward Tabulation <n> tab stops */
 	case 'J': /* ED -- Clear screen */
 		sel.bx = -1;
 		switch(escseq.arg[0]) {
@@ -1429,8 +1428,11 @@ csireset(void) {
 
 void
 tputtab(void) {
-	int space = TAB - term.c.x % TAB;
-	tmoveto(term.c.x + space, term.c.y);
+	unsigned x;
+
+	for (x = term.c.x + 1; x < term.col && !term.tabs[x]; ++x)
+		/* nothing */ ;
+	tmoveto(x, term.c.y);
 }
 
 void
@@ -1491,6 +1493,10 @@ tputc(char *c) {
 				tnewline(1); /* always go to first col */
 				term.esc = 0;
 				break;
+			case 'H': /* HTS -- Horizontal tab stop */
+				term.tabs[term.c.x] = 1;
+				term.esc = 0;
+				break;
 			case 'M': /* RI -- Reverse index */
 				if(term.c.y == term.top)
 					tscrolldown(term.top, 1);
-- 
1.7.10.4

>From 3c238633d2679c1fa66b200fe9aa6dcc15a9ebff Mon Sep 17 00:00:00 2001
From: "Roberto E. Vargas Caballero" <k...@shike2.com>
Date: Wed, 15 Aug 2012 10:31:37 +0200
Subject: [PATCH 3/3] Add TBC sequence

This sequence clears tab stops in the terminal. If the argument is not present
or is zero, then removes the tab stop of the current horizontal position. If
the argument is 3 then removes all the tab stops of the terminal. It was
necessary modify the terminfo entry tbc, because it has \E[2g instead of the
correct \E[3g.

Signed-off-by: Roberto E. Vargas Caballero <k...@shike2.com>
---
 st.c    |   12 ++++++++++++
 st.info |    2 +-
 2 files changed, 13 insertions(+), 1 deletion(-)

diff --git a/st.c b/st.c
index 4b7e4eb..b7dfd55 100644
--- a/st.c
+++ b/st.c
@@ -1203,6 +1203,18 @@ csihandle(void) {
 		DEFAULT(escseq.arg[0], 1);
 		tmoveto(0, term.c.y-escseq.arg[0]);
 		break;
+	case 'g': /* TBC -- Tabulation clear */
+		switch (escseq.arg[0]) {
+		case 0: /* clear current tab stop */
+			term.tabs[term.c.x] = 0;
+			break;
+		case 3: /* clear all the tabs */
+			memset(term.tabs, 0, term.col * sizeof(*term.tabs));
+			break;
+		default:
+			goto unknown;
+		}
+		break;
 	case 'G': /* CHA -- Move to <col> */
 	case '`': /* XXX: HPA -- same? */
 		DEFAULT(escseq.arg[0], 1);
diff --git a/st.info b/st.info
index ea67039..d8e3d0d 100644
--- a/st.info
+++ b/st.info
@@ -97,7 +97,7 @@ st| simpleterm,
 	smcup=\E[?1049h,
 	smso=\E[7m,
 	smul=\E[4m,
-	tbc=\E[2g,
+	tbc=\E[3g,
 	tsl=\E]0;,
 	ul,
 	xenl,
-- 
1.7.10.4

Reply via email to