From d4fa0d3904fb0dfc8194174f00519e4420592d85 Mon Sep 17 00:00:00 2001 From: Chris Allegretta Date: Tue, 5 Mar 2002 19:55:55 +0000 Subject: [PATCH] justify_format(), do_justify() - Various fixes for starting blank spaces, spaces after punctuation, & segfault with quoting strings (David Benbennick) git-svn-id: svn://svn.savannah.gnu.org/nano/trunk/nano@1103 35c25a1d-7b9e-4130-9fde-d3aeb78583b8 --- ChangeLog | 12 +++++++++--- nano.c | 57 ++++++++++++++++++++++++++++++++++++------------------- proto.h | 1 + winio.c | 9 +++++++-- 4 files changed, 55 insertions(+), 24 deletions(-) diff --git a/ChangeLog b/ChangeLog index ea7ebae6..c59abdc9 100644 --- a/ChangeLog +++ b/ChangeLog @@ -54,6 +54,9 @@ CVS code - - nano.1: - Added Noconvert option to man page (DLR). - nano.c: + justify_format(), do_justify() + - Various fixes for starting blank spaces, spaces after + punctuation, & segfault with quoting strings (David Benbennick). help_init() - Added message re: having multiple blank buffers (DLR). main() @@ -71,14 +74,17 @@ CVS code - bottombars(), onekey() - Make bottom list dynamic with screen size (Guus Sliepen & Chris). - More cleanups w/width of shortcut. -- utils.c: - strstrwrapper() - - NANO_SMALL test was backwards (Ken Tyler). - utils.c: strcasestr(),revstrcasestr() - Renamed to stristr and revstristr since strcasestr has not been confirmed to be detected properly on various Linux systems. + strstrwrapper() + - NANO_SMALL test was backwards (Ken Tyler). +- winio.c: + strlenpt() + - Changed main function to strnlenpt() for new justify changes, + original function now just a stub. - nanorc.sample - Mention unset in the sample nanorc. - po/ca.po, po/es.po: diff --git a/nano.c b/nano.c index 814b6f2b..5e50e4c7 100644 --- a/nano.c +++ b/nano.c @@ -2201,8 +2201,8 @@ void justify_format(char *data) int i = 0; int len = strlen(data); - /* Skip first character regardless and leading whitespace. */ - for (i = 1; i < len; i++) { + /* Skip leading whitespace. */ + for (i = 0; i < len; i++) { if (!isspace((int) data[i])) break; } @@ -2212,12 +2212,21 @@ void justify_format(char *data) /* No double spaces allowed unless following a period. Tabs -> space. No double tabs. */ for (; i < len; i++) { if (isspace((int) data[i]) && isspace((int) data[i - 1]) - && (data[i - 2] != '.')) { + && (data[i - 2] != '.') + && (data[i-2]!='!') && (data[i-2]!='?')) { memmove(data + i, data + i + 1, len - i); len--; i--; } } + /* Skip trailing whitespace. + * i<=len iff there was a non-space in the line. In that case, we + * strip spaces from the end of the line. Note that "line" means the + * whole paragraph. */ + if (i<=len) { + for(i=len-1; i>0 && isspace((int) data[i]); i--); + data[i+1] = '\0'; + } } #endif @@ -2333,23 +2342,33 @@ int do_justify(void) int len2 = 0; filestruct *tmpline = nmalloc(sizeof(filestruct)); - /* Start at fill , unless line isn't that long (but it - * appears at least fill long with tabs. - */ - if (slen > fill) - i = fill; - else - i = slen; - - for (; i > 0; i--) { - if (isspace((int) current->data[i]) && - ((strlenpt(current->data) - strlen(current->data + i)) - <= fill)) - break; - } - if (!i) - break; +/* The following code maybe could be better. In particular, can we + * merely increment instead of calling strnlenpt for each new character? + * In fact, can we assume the only tabs are at the beginning of the line? + */ +/* Note that we CAN break before the first word, since that is how + * pico does it. */ + int last_space = -1; /* index of the last breakpoint */ + int allowed_width; + + i = qdepth * strlen(quotestr); /* the line starts with + indentation, so we must skip it! */ + allowed_width = fill - i; /* how wide can our lines be? */ + + for(; idata[i])) last_space = i; + if (last_space!=-1 && + strnlenpt(current->data,i) >= allowed_width) { + i = last_space; + break; + } + } +/* Now data[i] is a space. We want to break at the LAST space in this + * group. Probably, the only possibility is two in a row, but let's be + * generic. Note that we actually replace this final space with \0. Is + * this okay? It seems to work fine. */ + for(; idata[i+1]); i++) ; current->data[i] = '\0'; diff --git a/proto.h b/proto.h index 239bb8ea..e7aa3e5f 100644 --- a/proto.h +++ b/proto.h @@ -99,6 +99,7 @@ int free_filestruct(filestruct * src); int xplustabs(void); int do_yesno(int all, int leavecursor, char *msg, ...); int actual_x(filestruct * fileptr, int xplus); +int strnlenpt(char *buf, int size); int strlenpt(char *buf); int statusq(int allowtabs, shortcut s[], char *def, char *msg, ...); int write_file(char *name, int tmpfile, int append, int nonamechange); diff --git a/winio.c b/winio.c index 1ad69bde..892c0f18 100644 --- a/winio.c +++ b/winio.c @@ -134,14 +134,14 @@ int actual_x(filestruct * fileptr, int xplus) } /* a strlen with tabs factored in, similar to xplustabs() */ -int strlenpt(char *buf) +int strnlenpt(char *buf, int size) { int i, tabs = 0; if (buf == NULL) return 0; - for (i = 0; buf[i] != 0; i++) { + for (i = 0; i < size; i++) { tabs++; if (buf[i] == NANO_CONTROL_I) { @@ -158,6 +158,11 @@ int strlenpt(char *buf) return tabs; } +int strlenpt(char *buf) +{ + return strnlenpt(buf, strlen(buf)); +} + /* resets current_y, based on the position of current, and puts the cursor at (current_y, current_x) */ -- 2.39.5