Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
"]": "CL",
"}": "CL",
"`": "QU",
"'": "QU",
"\"": "QU",
".": "IS",
",": "IS",
":": "IS",
Expand Down
44 changes: 40 additions & 4 deletions lib/node_modules/@stdlib/_tools/repl-txt/wrap-text/lib/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,28 @@ var BREAK_CLASSES = require( './break_classes.json' );

// FUNCTIONS //

/**
* Determines whether a character at a specified position opens a quoted span.
*
* @private
* @param {string} text - input string
* @param {NonNegativeInteger} idx - character position
* @param {(string|null)} prev - break class of preceding character
* @returns {boolean} whether the character opens a quoted span
*/
function isQuoteStart( text, idx, prev ) {
var ch = text.charAt( idx );
if ( BREAK_CLASSES[ ch ] !== 'QU' ) {
return false;
}
// A quote character only opens a span at the start of a line or when following a space or open punctuation (e.g., an apostrophe in a contraction does not open a span):
if ( prev !== null && prev !== 'SP' && prev !== 'OP' ) {
return false;
}
// Require a matching closing character in order to avoid treating the remainder of a line as unbreakable:
return text.indexOf( ch, idx+1 ) !== -1;
}

/**
* Determines whether a break opportunity exists between two adjacent characters.
*
Expand Down Expand Up @@ -74,23 +96,37 @@ function canBreak( prev, next ) {
*/
function findBreakUnits( text ) {
var segments;
var quote;
var start;
var prev;
var curr;
var len;
var ch;
var i;

len = text.length;
segments = [];
start = 0;
prev = BREAK_CLASSES[ text.charAt( 0 ) ] || 'AL';

ch = text.charAt( 0 );
prev = BREAK_CLASSES[ ch ] || 'AL';
quote = '';
if ( isQuoteStart( text, 0, null ) ) {
quote = ch;
}
for ( i = 1; i < len; i++ ) {
curr = BREAK_CLASSES[ text.charAt( i ) ] || 'AL';
if ( canBreak( prev, curr ) ) {
ch = text.charAt( i );
curr = BREAK_CLASSES[ ch ] || 'AL';

// Suppress break opportunities within quoted spans so that a span is always kept intact:
if ( quote === '' && canBreak( prev, curr ) ) {
segments.push( text.substring( start, i ) );
start = i;
}
if ( quote === ch ) {
quote = '';
} else if ( quote === '' && isQuoteStart( text, i, prev ) ) {
quote = ch;
}
prev = curr;
}
segments.push( text.substring( start ) );
Expand Down
147 changes: 147 additions & 0 deletions lib/node_modules/@stdlib/_tools/repl-txt/wrap-text/test/test.js
Original file line number Diff line number Diff line change
Expand Up @@ -237,6 +237,153 @@ tape( 'the function breaks at hyphens', function test( t ) {
t.end();
});

tape( 'the function does not break within backtick-delimited spans', function test( t ) {
var expected;
var actual;
var txt;

txt = 'Beep boop `-1`';

expected = ' Beep boop\n `-1`';

actual = wrap( txt, {
'indent': 4,
'maxWidth': 16
});

t.strictEqual( actual, expected, 'returns expected value' );
t.end();
});

tape( 'the function does not break within single-quoted spans', function test( t ) {
var expected;
var actual;
var txt;

txt = 'Beep boop \'hello world\'';

expected = ' Beep boop\n \'hello world\'';

actual = wrap( txt, {
'indent': 4,
'maxWidth': 20
});

t.strictEqual( actual, expected, 'returns expected value' );
t.end();
});

tape( 'the function does not break within double-quoted spans', function test( t ) {
var expected;
var actual;
var txt;

txt = 'Beep boop "hello world"';

expected = ' Beep boop\n "hello world"';

actual = wrap( txt, {
'indent': 4,
'maxWidth': 20
});

t.strictEqual( actual, expected, 'returns expected value' );
t.end();
});

tape( 'the function does not treat an apostrophe within a word as opening a quoted span', function test( t ) {
var expected;
var actual;
var txt;

txt = 'The function doesn\'t break when a word\'s apostrophe appears mid-sentence.';

expected = ' The function doesn\'t break when a\n word\'s apostrophe appears mid-\n sentence.';

actual = wrap( txt, {
'indent': 4,
'maxWidth': 40
});

t.strictEqual( actual, expected, 'returns expected value' );
t.end();
});

tape( 'the function ignores unmatched quote characters', function test( t ) {
var expected;
var actual;
var txt;

txt = 'An unmatched ` backtick must not prevent wrapping of subsequent text.';

expected = ' An unmatched ` backtick must not\n prevent wrapping of subsequent text.';

actual = wrap( txt, {
'indent': 4,
'maxWidth': 40
});

t.strictEqual( actual, expected, 'returns expected value' );
t.end();
});

tape( 'the function wraps text containing quoted spans', function test( t ) {
var expected;
var actual;
var txt;

txt = 'Rendering mode. If `true`, an instance renders on each \'change\' event; otherwise, rendering must be triggered manually.';

expected = ' Rendering mode. If `true`, an instance renders on each \'change\' event;\n otherwise, rendering must be triggered manually.';

actual = wrap( txt );

t.strictEqual( actual, expected, 'returns expected value' );
t.end();
});

tape( 'the function preserves table rows and does not break quoted spans', function test( t ) {
var expected;
var actual;
var txt;

txt = [
'Returns a sparkline up/down chart instance.',
'',
'Glyphs:',
'',
'| Value | Glyph |',
'|:-----:|:-----:|',
'| 1 | ↑ |',
'| -1 | ↓ |',
'',
'If provided any other value other than 1 or `-1`, the value is encoded as a missing value.',
'',
'The `data` argument takes precedence over the `data` option.'
].join( '\n' );

expected = [
' Returns a sparkline up/down chart instance.',
'',
' Glyphs:',
'',
' | Value | Glyph |',
' |:-----:|:-----:|',
' | 1 | ↑ |',
' | -1 | ↓ |',
'',
' If provided any other value other than 1 or `-1`, the value is encoded as a',
' missing value.',
'',
' The `data` argument takes precedence over the `data` option.'
].join( '\n' );

actual = wrap( txt );

t.strictEqual( actual, expected, 'returns expected value' );
t.end();
});

tape( 'the function supports custom indent levels', function test( t ) {
var expected;
var actual;
Expand Down
Loading