shithub: neatroff

Download patch

ref: 728e4356eb13cdc0a41440264099299676f27d3d
parent: 046f8565a5a858c2201b4fcfef4daa65842d2b54
author: Ali Gholami Rudi <ali@rudi.ir>
date: Thu Nov 29 18:39:12 EST 2012

no filling mode

--- a/ren.c
+++ b/ren.c
@@ -47,55 +47,92 @@
 	return l;
 }
 
-static void adjust(char *s, int adj)
+static void adjust_nf(char *s, int n)
 {
-	struct word *last = words;
 	struct word *cur;
-	int w = 0;
 	int lendiff;
+	int w = 0;
 	int i;
-	int adj_div = 0;
-	int adj_rem = 0;
-	int n;
-	while (last < words + nwords && w + last->wid + last->blanks <= LL) {
-		w += last->wid + last->blanks;
-		last++;
-	}
-	if (last > words)
-		last--;
-	n = last - words + 1;
-	if (adj && n > 1) {
-		adj_div = (LL - w) / (n - 1);
-		adj_rem = LL - w - adj_div * (n - 1);
-	}
-	for (i = 0; i < n - 1; i++)
-		words[i + 1].blanks += adj_div + (i < adj_rem);
-	for (cur = words; cur <= last; cur++) {
+	for (i = 0; i < n; i++) {
+		cur = &words[i];
 		s += sprintf(s, "\\h'%du'", cur->blanks);
 		memcpy(s, buf + cur->beg, cur->end - cur->beg);
 		s += cur->end - cur->beg;
+		w += cur->wid + cur->blanks;
 	}
 	*s = '\0';
-	lendiff = n < nwords ? last[1].beg : buflen;
+	lendiff = n < nwords ? words[n].beg : buflen;
 	memmove(buf, buf + lendiff, buflen - lendiff);
 	buflen -= lendiff;
 	nwords -= n;
-	memmove(words, last + 1, nwords * sizeof(words[0]));
+	memmove(words, words + n, nwords * sizeof(words[0]));
 	wid -= w;
 	for (i = 0; i < nwords; i++) {
 		words[i].beg -= lendiff;
 		words[i].end -= lendiff;
 	}
+}
+
+static void adjust_fi(char *s, int adj)
+{
+	int adj_div, adj_rem;
+	int w = 0;
+	int i, n;
+	for (n = 0; n < nwords; n++) {
+		if (n && w + words[n].wid + words[n].blanks > LL)
+			break;
+		w += words[n].wid + words[n].blanks;
+	}
+	if (adj == ADJ_B && n > 1 && n < nwords) {
+		adj_div = (LL - w) / (n - 1);
+		adj_rem = LL - w - adj_div * (n - 1);
+		wid += LL - w;
+		for (i = 0; i < n - 1; i++)
+			words[i + 1].blanks += adj_div + (i < adj_rem);
+	}
+	adjust_nf(s, n);
 	if (nwords)
 		wid -= words[0].blanks;
 	words[0].blanks = 0;
 }
 
-static void ren_br(int sp, int adj);
+static void ren_ne(int n)
+{
+	if (n_nl + n > n_p)
+		ren_page(n_pg + 1);
+}
 
+static void down(int n)
+{
+	n_d += n;
+	n_nl = n_d;
+	if (n_nl <= n_p)
+		printf("v%d\n", n);
+	ren_ne(0);
+}
+
+static void ren_br(int sp)
+{
+	char out[LNLEN];
+	buf[buflen] = '\0';
+	if (nwords) {
+		if (n_u)
+			adjust_fi(out, n_ad);
+		else
+			adjust_nf(out, nwords);
+		ren_ne(n_v);
+		down(n_v);
+		printf("H%d\n", n_o + n_i);
+		output(out);
+		ren_ne(n_v);
+	}
+	if (sp)
+		down(sp);
+}
+
 void tr_br(char **args)
 {
-	ren_br(0, 0);
+	ren_br(0);
 }
 
 void tr_sp(char **args)
@@ -103,7 +140,7 @@
 	int sp = 0;
 	if (args[1])
 		sp = tr_int(args[1], 0, 'v');
-	ren_br(sp, 0);
+	ren_br(sp);
 }
 
 void ren_page(int pg)
@@ -117,7 +154,7 @@
 
 void tr_bp(char **args)
 {
-	ren_br(0, 0);
+	ren_br(0);
 	ren_page(args[1] ? tr_int(args[1], n_pg, 'v') : n_pg + 1);
 }
 
@@ -136,7 +173,7 @@
 
 void tr_in(char **args)
 {
-	ren_br(0, 0);
+	ren_br(0);
 	if (args[1])
 		n_i = tr_int(args[1], n_i, 'm');
 }
@@ -164,6 +201,12 @@
 		errmsg("troff: failed to mount %s\n", args[2]);
 }
 
+void tr_nf(char **args)
+{
+	ren_br(0);
+	n_u = 0;
+}
+
 static void escarg(char *s, int cmd)
 {
 	int c;
@@ -199,37 +242,6 @@
 	*s = '\0';
 }
 
-static void ren_ne(int n)
-{
-	if (n_nl + n > n_p)
-		ren_page(n_pg + 1);
-}
-
-static void down(int n)
-{
-	n_d += n;
-	n_nl = n_d;
-	if (n_nl <= n_p)
-		printf("v%d\n", n);
-	ren_ne(0);
-}
-
-static void ren_br(int sp, int adj)
-{
-	char out[LNLEN];
-	buf[buflen] = '\0';
-	if (nwords) {
-		adjust(out, wid > LL ? n_ad : adj);
-		ren_ne(n_v);
-		down(n_v);
-		printf("H%d\n", n_o + n_i);
-		output(out);
-		ren_ne(n_v);
-	}
-	if (sp)
-		down(sp);
-}
-
 void render(void)
 {
 	char c[GNLEN * 2];
@@ -242,21 +254,23 @@
 	int r_f = n_f;
 	int esc = 0;
 	int space_br = 0;	/* .br caused by indented lines */
-	ren_br(0, 0);
+	ren_br(0);
 	while (nextchar(c) > 0) {
 		g = NULL;
-		if (!word && wid > LL)
-			ren_br(0, wid > LL ? n_ad : 0);
+		if (n_u && !word && wid > LL)
+			ren_br(0);
 		if (c[0] == ' ' || c[0] == '\n') {
 			if (word) {
 				word->end = buflen;
 				word = NULL;
 			}
-			if (newline && c[0] == '\n')
-				ren_br(n_v, 0);
-			if (newline && c[0] == ' ' && !space_br) {
+			if (!n_u && c[0] == '\n')
+				ren_br(0);
+			if (n_u && newline && c[0] == '\n')
+				ren_br(n_v);
+			if (n_u && newline && c[0] == ' ' && !space_br) {
 				space_br = 1;
-				ren_br(0, 0);
+				ren_br(0);
 			}
 			if (c[0] == '\n') {
 				blanks = 0;
@@ -313,6 +327,7 @@
 		word->wid += g_wid;
 		wid += g_wid;
 	}
-	ren_br(0, wid > LL ? n_ad : 0);
-	ren_br(0, 0);
+	if (n_u)
+		ren_br(0);
+	ren_br(0);
 }
--- a/tr.c
+++ b/tr.c
@@ -269,6 +269,7 @@
 	{"in", tr_in},
 	{"ll", tr_ll},
 	{"na", tr_na},
+	{"nf", tr_nf},
 	{"nr", tr_nr, mkargs_reg1},
 	{"pl", tr_pl},
 	{"ps", tr_ps},
--- a/xroff.c
+++ b/xroff.c
@@ -17,6 +17,7 @@
 	n_l = SC_IN * 65 / 10;
 	n_i = 0;
 	n_s = 10;
+	n_u = 1;
 	n_v = 12 * SC_PT;
 	n_s0 = n_s;
 	n_f0 = n_f;
--- a/xroff.h
+++ b/xroff.h
@@ -14,6 +14,10 @@
 #define NARGS		9	/* number of macro arguments */
 #define RLEN		4	/* register/macro name */
 
+/* adjustment modes */
+#define ADJ_L		0
+#define ADJ_B		1
+
 #define LEN(a)		(sizeof(a) / sizeof((a)[0]))
 
 /* number registers */
@@ -35,6 +39,7 @@
 #define n_o		nreg[REG('.', 'o')]
 #define n_p		nreg[REG('.', 'p')]
 #define n_s		nreg[REG('.', 's')]
+#define n_u		nreg[REG('.', 'u')]
 #define n_v		nreg[REG('.', 'v')]
 #define n_nl		nreg[REG('n', 'l')]
 #define n_pg		nreg[REG('%', '\0')]	/* % */
@@ -105,6 +110,7 @@
 void tr_fp(char **args);
 void tr_ft(char **args);
 void tr_in(char **args);
+void tr_nf(char **args);
 void tr_nr(char **args);
 void tr_ps(char **args);
 void tr_sp(char **args);