new feature: allow lines to be softwrapped at whitespace
Extend get_softwrap_breakpoint() to break softwrapped lines on whitespace when a flag is set. This flag is controlled by the new rcfile option "atblanks". The '>' characters marking two-column characters at the edge of the screen are disabled when it's on. If get_softwrap_breakpoint() can't find whitespace in screen range, it will break the line on the screen edge. (In this case, a blank can be on the last column of the screen, but text can't, so that a blank on the last column doesn't become invisible and possibly break the display.) This fulfills https://savannah.gnu.org/bugs/index.php?49959. Requested-by: Nicholas Boel <axxisd@gmail.com>
Этот коммит содержится в:
родитель
aa04ad4f83
Коммит
bb4d0d548a
@ -657,6 +657,10 @@ When backing up files, allow the backup to succeed even if its
|
|||||||
permissions can't be (re)set due to special OS considerations.
|
permissions can't be (re)set due to special OS considerations.
|
||||||
You should NOT enable this option unless you are sure you need it.
|
You should NOT enable this option unless you are sure you need it.
|
||||||
|
|
||||||
|
@item set atblanks
|
||||||
|
When soft line wrapping is enabled, make it wrap lines at blank characters
|
||||||
|
(tabs and spaces) instead of always at the edge of the screen.
|
||||||
|
|
||||||
@item set autoindent
|
@item set autoindent
|
||||||
Use auto-indentation.
|
Use auto-indentation.
|
||||||
|
|
||||||
|
@ -57,6 +57,10 @@ When backing up files, allow the backup to succeed even if its permissions
|
|||||||
can't be (re)set due to special OS considerations. You should
|
can't be (re)set due to special OS considerations. You should
|
||||||
NOT enable this option unless you are sure you need it.
|
NOT enable this option unless you are sure you need it.
|
||||||
.TP
|
.TP
|
||||||
|
.B set atblanks
|
||||||
|
When soft line wrapping is enabled, make it wrap lines at blank characters
|
||||||
|
(tabs and spaces) instead of always at the edge of the screen.
|
||||||
|
.TP
|
||||||
.B set autoindent
|
.B set autoindent
|
||||||
Use auto-indentation.
|
Use auto-indentation.
|
||||||
.TP
|
.TP
|
||||||
|
@ -20,6 +20,10 @@
|
|||||||
## versions of nano installed (e.g. your home directory is on NFS).
|
## versions of nano installed (e.g. your home directory is on NFS).
|
||||||
# set quiet
|
# set quiet
|
||||||
|
|
||||||
|
## When soft line wrapping is enabled, make it wrap lines at blanks
|
||||||
|
## (tabs and spaces) instead of always at the edge of the screen.
|
||||||
|
# set atblanks
|
||||||
|
|
||||||
## Use auto-indentation.
|
## Use auto-indentation.
|
||||||
# set autoindent
|
# set autoindent
|
||||||
|
|
||||||
|
@ -521,7 +521,8 @@ enum
|
|||||||
JUSTIFY_TRIM,
|
JUSTIFY_TRIM,
|
||||||
SHOW_CURSOR,
|
SHOW_CURSOR,
|
||||||
LINE_NUMBERS,
|
LINE_NUMBERS,
|
||||||
NO_PAUSES
|
NO_PAUSES,
|
||||||
|
AT_BLANKS
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Flags for the menus in which a given function should be present. */
|
/* Flags for the menus in which a given function should be present. */
|
||||||
|
@ -90,6 +90,7 @@ static const rcoption rcopts[] = {
|
|||||||
{"view", VIEW_MODE},
|
{"view", VIEW_MODE},
|
||||||
#ifndef NANO_TINY
|
#ifndef NANO_TINY
|
||||||
{"allow_insecure_backup", INSECURE_BACKUP},
|
{"allow_insecure_backup", INSECURE_BACKUP},
|
||||||
|
{"atblanks", AT_BLANKS},
|
||||||
{"autoindent", AUTOINDENT},
|
{"autoindent", AUTOINDENT},
|
||||||
{"backup", BACKUP_FILE},
|
{"backup", BACKUP_FILE},
|
||||||
{"backupdir", 0},
|
{"backupdir", 0},
|
||||||
|
38
src/winio.c
38
src/winio.c
@ -2782,8 +2782,9 @@ int update_softwrapped_line(filestruct *fileptr)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
/* If the line is softwrapped before its last column, add a ">" just
|
/* If the line is softwrapped before its last column, add a ">" just
|
||||||
* after its softwrap breakpoint. */
|
* after its softwrap breakpoint, unless we're softwrapping at blanks
|
||||||
if (to_col - from_col < editwincols)
|
* and not in the middle of a word. */
|
||||||
|
if (!ISSET(AT_BLANKS) && to_col - from_col < editwincols)
|
||||||
mvwaddch(edit, row - 1, to_col - from_col, '>');
|
mvwaddch(edit, row - 1, to_col - from_col, '>');
|
||||||
|
|
||||||
from_col = to_col;
|
from_col = to_col;
|
||||||
@ -2993,12 +2994,20 @@ void edit_scroll(scroll_dir direction, int nrows)
|
|||||||
size_t get_softwrap_breakpoint(const char *text, size_t leftedge,
|
size_t get_softwrap_breakpoint(const char *text, size_t leftedge,
|
||||||
bool *end_of_line)
|
bool *end_of_line)
|
||||||
{
|
{
|
||||||
|
size_t index = 0;
|
||||||
|
/* Current index in text. */
|
||||||
size_t column = 0;
|
size_t column = 0;
|
||||||
/* Current column position in text. */
|
/* Current column position in text. */
|
||||||
size_t prev_column = 0;
|
size_t prev_column = 0;
|
||||||
/* Previous column position in text. */
|
/* Previous column position in text. */
|
||||||
size_t goal_column;
|
size_t goal_column;
|
||||||
/* Column of the last character where we can break the text. */
|
/* Column of the last character where we can break the text. */
|
||||||
|
bool found_blank = FALSE;
|
||||||
|
/* Did we find at least one blank? */
|
||||||
|
size_t lastblank_index = 0;
|
||||||
|
/* Current index of the last blank in text. */
|
||||||
|
size_t lastblank_column = 0;
|
||||||
|
/* Current column position of the last blank in text. */
|
||||||
int char_len = 0;
|
int char_len = 0;
|
||||||
/* Length of current character, in bytes. */
|
/* Length of current character, in bytes. */
|
||||||
|
|
||||||
@ -3007,13 +3016,26 @@ size_t get_softwrap_breakpoint(const char *text, size_t leftedge,
|
|||||||
while (*text != '\0' && column < leftedge)
|
while (*text != '\0' && column < leftedge)
|
||||||
text += parse_mbchar(text, NULL, &column);
|
text += parse_mbchar(text, NULL, &column);
|
||||||
|
|
||||||
/* Use a full screen row for text. */
|
/* Use a full screen row for text, or, if we're softwrapping at blanks, use
|
||||||
goal_column = column + editwincols;
|
* a full screen row less one column for text and reserve the last column
|
||||||
|
* for blanks. The latter case is to ensure that we have enough room for
|
||||||
|
* blanks exactly on the last column of the screen. */
|
||||||
|
if (ISSET(AT_BLANKS) && editwincols > 2)
|
||||||
|
goal_column = column + (editwincols - 1);
|
||||||
|
else
|
||||||
|
goal_column = column + editwincols;
|
||||||
|
|
||||||
while (*text != '\0' && column <= goal_column) {
|
while (*text != '\0' && column <= goal_column) {
|
||||||
|
if (ISSET(AT_BLANKS) && editwincols > 2 && is_blank_mbchar(text)) {
|
||||||
|
found_blank = TRUE;
|
||||||
|
lastblank_index = index;
|
||||||
|
lastblank_column = column;
|
||||||
|
}
|
||||||
|
|
||||||
prev_column = column;
|
prev_column = column;
|
||||||
char_len = parse_mbchar(text, NULL, &column);
|
char_len = parse_mbchar(text, NULL, &column);
|
||||||
text += char_len;
|
text += char_len;
|
||||||
|
index += char_len;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* If the text displays within goal_column, we've reached the end of the
|
/* If the text displays within goal_column, we've reached the end of the
|
||||||
@ -3023,6 +3045,14 @@ size_t get_softwrap_breakpoint(const char *text, size_t leftedge,
|
|||||||
return column;
|
return column;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* If we're softwrapping at blanks and we found at least one blank, move
|
||||||
|
* the pointer back to the last blank, step beyond it, and we're done. */
|
||||||
|
if (found_blank) {
|
||||||
|
text = text - index + lastblank_index;
|
||||||
|
parse_mbchar(text, NULL, &lastblank_column);
|
||||||
|
return lastblank_column;
|
||||||
|
}
|
||||||
|
|
||||||
/* Otherwise, return the column of the last character before goal_column,
|
/* Otherwise, return the column of the last character before goal_column,
|
||||||
* since we can't break the text anywhere else. */
|
* since we can't break the text anywhere else. */
|
||||||
return (editwincols > 2) ? prev_column : column - 1;
|
return (editwincols > 2) ? prev_column : column - 1;
|
||||||
|
@ -7,7 +7,7 @@ comment "#"
|
|||||||
icolor brightred "^[[:space:]]*((un)?(bind|set)|include|syntax|header|comment|magic|linter|i?color|extendsyntax).*$"
|
icolor brightred "^[[:space:]]*((un)?(bind|set)|include|syntax|header|comment|magic|linter|i?color|extendsyntax).*$"
|
||||||
|
|
||||||
# Keywords
|
# Keywords
|
||||||
icolor brightgreen "^[[:space:]]*(set|unset)[[:space:]]+(allow_insecure_backup|autoindent|backup|backwards|boldtext|casesensitive|constantshow|cut|fill[[:space:]]+-?[[:digit:]]+|historylog|justifytrim|linenumbers|locking|morespace|mouse|multibuffer|noconvert|nohelp|nopauses|nonewlines|nowrap|positionlog|preserve|quickblank|quiet|rebinddelete|rebindkeypad|regexp|showcursor|smarthome|smooth|softwrap|suspend|tabsize[[:space:]]+[1-9][0-9]*|tabstospaces|tempfile|unix|view|wordbounds)\>"
|
icolor brightgreen "^[[:space:]]*(set|unset)[[:space:]]+(allow_insecure_backup|atblanks|autoindent|backup|backwards|boldtext|casesensitive|constantshow|cut|fill[[:space:]]+-?[[:digit:]]+|historylog|justifytrim|linenumbers|locking|morespace|mouse|multibuffer|noconvert|nohelp|nopauses|nonewlines|nowrap|positionlog|preserve|quickblank|quiet|rebinddelete|rebindkeypad|regexp|showcursor|smarthome|smooth|softwrap|suspend|tabsize[[:space:]]+[1-9][0-9]*|tabstospaces|tempfile|unix|view|wordbounds)\>"
|
||||||
icolor yellow "^[[:space:]]*set[[:space:]]+((function|key|number|status|title)color)[[:space:]]+(bright)?(white|black|red|blue|green|yellow|magenta|cyan)?(,(white|black|red|blue|green|yellow|magenta|cyan))?\>"
|
icolor yellow "^[[:space:]]*set[[:space:]]+((function|key|number|status|title)color)[[:space:]]+(bright)?(white|black|red|blue|green|yellow|magenta|cyan)?(,(white|black|red|blue|green|yellow|magenta|cyan))?\>"
|
||||||
icolor brightgreen "^[[:space:]]*set[[:space:]]+(backupdir|brackets|functioncolor|keycolor|matchbrackets|numbercolor|operatingdir|punct|quotestr|speller|statuscolor|titlecolor|whitespace|wordchars)[[:space:]]+"
|
icolor brightgreen "^[[:space:]]*set[[:space:]]+(backupdir|brackets|functioncolor|keycolor|matchbrackets|numbercolor|operatingdir|punct|quotestr|speller|statuscolor|titlecolor|whitespace|wordchars)[[:space:]]+"
|
||||||
icolor brightgreen "^[[:space:]]*bind[[:space:]]+((\^([[:alpha:]]|[]0-9\^_]|Space)|M-([[:alpha:]]|[]!"#$%&'()*+,./0-9:;<=>?@\^_`{|}~-]|Space))|F([1-9]|1[0-6])|Ins|Del)[[:space:]]+[[:alpha:]]+[[:space:]]+(all|main|search|replace(with)?|gotoline|writeout|insert|ext(ernal)?cmd|help|spell|linter|browser|whereisfile|gotodir)([[:space:]]+#|[[:space:]]*$)"
|
icolor brightgreen "^[[:space:]]*bind[[:space:]]+((\^([[:alpha:]]|[]0-9\^_]|Space)|M-([[:alpha:]]|[]!"#$%&'()*+,./0-9:;<=>?@\^_`{|}~-]|Space))|F([1-9]|1[0-6])|Ins|Del)[[:space:]]+[[:alpha:]]+[[:space:]]+(all|main|search|replace(with)?|gotoline|writeout|insert|ext(ernal)?cmd|help|spell|linter|browser|whereisfile|gotodir)([[:space:]]+#|[[:space:]]*$)"
|
||||||
|
Загрузка…
x
Ссылка в новой задаче
Block a user