diff --git a/doc/nano.texi b/doc/nano.texi
index 02140e0b70e970a3397e838a0ade571ca414ec45..aad6b77a73fbae6a2f2458b4e836e8d8658a8821 100644
--- a/doc/nano.texi
+++ b/doc/nano.texi
@@ -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.
 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
 Use auto-indentation.
 
diff --git a/doc/nanorc.5 b/doc/nanorc.5
index 9e4a983f9c20a25ed1563cfe3c8d024dbe18eff7..5671d57081090eedd1cb63fcb645854573e5c9a8 100644
--- a/doc/nanorc.5
+++ b/doc/nanorc.5
@@ -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
 NOT enable this option unless you are sure you need it.
 .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
 Use auto-indentation.
 .TP
diff --git a/doc/sample.nanorc.in b/doc/sample.nanorc.in
index 07c706bcb7d94ee4226bef76173e10ea988d76a4..fc66a1d4f55c0f258f442671689a5de6807f27b8 100644
--- a/doc/sample.nanorc.in
+++ b/doc/sample.nanorc.in
@@ -20,6 +20,10 @@
 ## versions of nano installed (e.g. your home directory is on NFS).
 # 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.
 # set autoindent
 
diff --git a/src/nano.h b/src/nano.h
index 113512f636624ebc0a6d60dc9f953d9997773b96..6c6992092805a56a4c74436ee3fd1155e541c41e 100644
--- a/src/nano.h
+++ b/src/nano.h
@@ -521,7 +521,8 @@ enum
     JUSTIFY_TRIM,
     SHOW_CURSOR,
     LINE_NUMBERS,
-    NO_PAUSES
+    NO_PAUSES,
+    AT_BLANKS
 };
 
 /* Flags for the menus in which a given function should be present. */
diff --git a/src/rcfile.c b/src/rcfile.c
index 6d7a20be9f81354e387283b37dc4e8899ed8f910..8505e0c726cc4525adc163baf1134dda606862b4 100644
--- a/src/rcfile.c
+++ b/src/rcfile.c
@@ -90,6 +90,7 @@ static const rcoption rcopts[] = {
     {"view", VIEW_MODE},
 #ifndef NANO_TINY
     {"allow_insecure_backup", INSECURE_BACKUP},
+    {"atblanks", AT_BLANKS},
     {"autoindent", AUTOINDENT},
     {"backup", BACKUP_FILE},
     {"backupdir", 0},
diff --git a/src/winio.c b/src/winio.c
index 8c1edcfd93c894eb216917651667491c234498e0..414c30ce144fefe6a6cb691d21c80b7ae28130c8 100644
--- a/src/winio.c
+++ b/src/winio.c
@@ -2782,8 +2782,9 @@ int update_softwrapped_line(filestruct *fileptr)
 	    break;
 
 	/* If the line is softwrapped before its last column, add a ">" just
-	 * after its softwrap breakpoint. */
-	if (to_col - from_col < editwincols)
+	 * after its softwrap breakpoint, unless we're softwrapping at blanks
+	 * 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, '>');
 
 	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,
 				bool *end_of_line)
 {
+    size_t index = 0;
+	/* Current index in text. */
     size_t column = 0;
 	/* Current column position in text. */
     size_t prev_column = 0;
 	/* Previous column position in text. */
     size_t goal_column;
 	/* 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;
 	/* 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)
 	text += parse_mbchar(text, NULL, &column);
 
-    /* Use a full screen row for text. */
-    goal_column = column + editwincols;
+    /* Use a full screen row for text, or, if we're softwrapping at blanks, use
+     * 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) {
+	if (ISSET(AT_BLANKS) && editwincols > 2 && is_blank_mbchar(text)) {
+	    found_blank = TRUE;
+	    lastblank_index = index;
+	    lastblank_column = column;
+	}
+
 	prev_column = column;
 	char_len = parse_mbchar(text, NULL, &column);
 	text += char_len;
+	index += char_len;
     }
 
     /* 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;
     }
 
+    /* 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,
      * since we can't break the text anywhere else. */
     return (editwincols > 2) ? prev_column : column - 1;
diff --git a/syntax/nanorc.nanorc b/syntax/nanorc.nanorc
index 2cf4e5f8e0250708393025aaf909e529ee4c56cf..de293685d9f5f05da9a5d6fa94478fb0e1091d81 100644
--- a/syntax/nanorc.nanorc
+++ b/syntax/nanorc.nanorc
@@ -7,7 +7,7 @@ comment "#"
 icolor brightred "^[[:space:]]*((un)?(bind|set)|include|syntax|header|comment|magic|linter|i?color|extendsyntax).*$"
 
 # 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 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:]]*$)"