Wrap lines using Unicode UAX #14 line breaking rules.
npm install @cto.af/linewrap
A command line interface is available: @cto.af/linewrap-cli
import {LineWrap} from '@cto.af/linewrap'
const w = new LineWrap()
w.wrap('Lorem ipsum dolor sit amet...') // A string, wrapped to your console length
for (const line of w.lines('Lorem ipsum dolor sit amet...')) {
// `line` does not have a newline at the end
}
Full API docs are available.
- wrap(string)
- Sometimes, you just want text out of the wrapping operation, with newlines
between the lines. Use
wrap()
for this. Note that there is no newline at the end of the wrapped text. - *lines(string)
- Sometimes, you'll want the lines individually; perhaps you're streaming, or
integrating the lines with other content. The
*lines()
method will return a string generator, where each line is NOT ended with a newline. Thewrap()
method just calls*lines()
and joins the result with your configured newline string.
Options may be passed into the constructor in an object:
const w = new LineWrap({ width: 40 })
The following options are all optional, having the specified defaults:
-
ellipsis: string = '…'
(U+2026: HORIZONTAL ELLIPSIS) - String to use when long word is truncated with
LineWrap.OVERFLOW_CLIP
. example7: boolean = false
- Turn on the extra rules for matching numbers from Example 7 of UAX #14
firstCol: number = NaN
- If indentFirst is false, how many columns was the first line already indented? If NaN, use the indent width, in graphemes. If indentFirst is true, this is ignored.
-
hyphen: string = '-'
(U+002D: HYPHEN-MINUS) - String to use when long word is split to next line with
LineWrap.OVERFLOW_ANYWHERE
. -
indent: number | string = ''
(empty string) - If a string, indent every line (except the first if indentFirst is false) with
that string. If a number, insert that many
indentChar
s at the beginning of each line. includeANSI: boolean = false
- If true, include ANSI escape sequences in the width of the string. If false, strips ANSI before calculating width.
-
indentChar: string = ' '
(U+0020: SPACE) - If
indent
is a number, use that many of this string to indent. indentEmpty: boolean = false
- If the input string is empty, should we still indent?
indentFirst : boolean = true
- Indent the first line? If not, treat the first line as if it was already
indented, giving a short first line. Use
firstCol
to control how short the first line should be. isCJK : boolean
- Override the locale, forcing strings to be measured in a Chinese/Japanese/Korean context or not.
isNewline : RegExp | null = /[^\S\r\n\v\f\x85\u2028\u2029]*[\r\n\v\f\x85\u2028\u2029]+\s*/gu
- Regular expression that finds newlines for replacement with
newlineReplacement
. Ensure you do not create a regular expression denial of service (ReDoS) attack. Make sure the expression has the `g` modifier. If null, no newline replacement is done, and existing newlines will be maintained in the output, no matter where they were originally. -
locale: string =
[system locale as determined by Intl.Segmenter] - Which locale to use when splitting by graphemes? May have a small effect in some locales. If you have experience with one of those locales, please file an issue or PR with examples so this can be tested carefully.
newline: string = '\n'
- String used to separate lines in the
wrap()
method. newlineReplacement: string = ' '
- For every newline found with
isNewline
, replace with this string. overflow: Symbol = LineWrapOptions.OVERFLOW_VISIBLE
- What to do with words that are longer than the available width? There are
three options:
-
LineWrapOptions.OVERFLOW_VISIBLE
: If a word is longer than the wrappable area, allow the word to go extend past the width so that it is not broken. This is the only way for long URLs to still be clickable. -
LineWrapOptions.OVERFLOW_CLIP
: If a word is longer than the wrappable area, cut it to size, dropping the rest of the word, inserting an ellipsis at the end. -
LineWrapOptions.OVERFLOW_ANYWHERE
: If a word is longer than the wrappable area, split it into chunks that do fit, inserting a hyphen at the end of each line.
-
verbose : boolean = false
- Enable output on stdout for deep diagnostic information. Only useful for debugging.
width: number = 80
- Maximum number of graphemes per line, including indentation.
escape: (x: string) => string = (x) => x
- Function to escape the input string. The escaping is performed after line breaking and grapheme counting, with the intent that in the final display, those escapes will be replaced appropriately. Defaults to an identity transform.