From e4a91a89e0040b94853526e9f29e30b88769c3e7 Mon Sep 17 00:00:00 2001 From: "Alex Lam S.L" Date: Fri, 28 Jan 2022 00:38:11 +0000 Subject: [PATCH] support custom indentation (#5318) closes #50 --- README.md | 6 ++- lib/output.js | 20 ++++--- lib/utils.js | 8 --- test/compress/indentation.js | 100 +++++++++++++++++++++++++++++++++++ 4 files changed, 118 insertions(+), 16 deletions(-) create mode 100644 test/compress/indentation.js diff --git a/README.md b/README.md index 22842e3f..60cb6ab8 100644 --- a/README.md +++ b/README.md @@ -917,9 +917,11 @@ can pass additional arguments that control the code output: - `galio` (default: `false`) — enable workarounds for ANT Galio bugs -- `indent_level` (default: `4`) +- `indent_level` (default: `4`) — indent by specified number of spaces or the + exact whitespace sequence supplied, e.g. `"\t"`. -- `indent_start` (default: `0`) — prefix all lines by that many spaces +- `indent_start` (default: `0`) — prefix all lines by whitespace sequence + specified in the same format as `indent_level`. - `inline_script` (default: `true`) — escape HTML comments and the slash in occurrences of `` in strings diff --git a/lib/output.js b/lib/output.js index 358e1931..b35fdb97 100644 --- a/lib/output.js +++ b/lib/output.js @@ -101,9 +101,17 @@ function OutputStream(options) { } } + function make_indent(value) { + if (typeof value == "number") return new Array(value + 1).join(" "); + if (!/^\s*$/.test(value)) throw new Error("unsupported indentation: " + JSON.stringify("" + value)); + return value; + } + var current_col = 0; var current_line = 1; - var indentation = options.indent_start; + var current_indent = make_indent(options.indent_start); + var full_indent = make_indent(options.indent_level); + var half_indent = full_indent.length + 1 >> 1; var last; var line_end = 0; var line_fixed = true; @@ -368,14 +376,14 @@ function OutputStream(options) { var indent = options.beautify ? function(half) { if (need_newline_indented) print("\n"); - print(repeat_string(" ", half ? indentation - (options.indent_level >> 1) : indentation)); + print(half ? current_indent.slice(0, -half_indent) : current_indent); } : noop; var with_indent = options.beautify ? function(cont) { - var save_indentation = indentation; - indentation += options.indent_level; + var save_indentation = current_indent; + current_indent += full_indent; cont(); - indentation = save_indentation; + current_indent = save_indentation; } : function(cont) { cont() }; var may_add_newline = options.max_line_len || options.preserve_line ? function() { @@ -559,7 +567,7 @@ function OutputStream(options) { reset : reset, indent : indent, should_break : options.beautify && options.width ? function() { - return current_col - indentation >= options.width; + return current_col >= options.width; } : return_false, has_parens : function() { return last.slice(-1) == "(" }, newline : newline, diff --git a/lib/utils.js b/lib/utils.js index 57122575..5b64af51 100644 --- a/lib/utils.js +++ b/lib/utils.js @@ -55,14 +55,6 @@ function find_if(func, array) { for (var i = array.length; --i >= 0;) if (func(array[i])) return array[i]; } -function repeat_string(str, i) { - if (i <= 0) return ""; - if (i == 1) return str; - var d = repeat_string(str, i >> 1); - d += d; - return i & 1 ? d + str : d; -} - function configure_error_stack(fn) { Object.defineProperty(fn.prototype, "stack", { get: function() { diff --git a/test/compress/indentation.js b/test/compress/indentation.js new file mode 100644 index 00000000..9eff2d7b --- /dev/null +++ b/test/compress/indentation.js @@ -0,0 +1,100 @@ +numeric: { + beautify = { + beautify: true, + indent_start: 1, + indent_level: 3, + } + input: { + switch (42) { + case null: + console.log("FAIL"); + } + console.log("PASS"); + } + expect_exact: [ + " switch (42) {", + " case null:", + ' console.log("FAIL");', + " }", + "", + ' console.log("PASS");', + ] + expect_stdout: "PASS" +} + +spaces: { + beautify = { + beautify: true, + indent_start: " ", + indent_level: " ", + } + input: { + switch (42) { + case null: + console.log("FAIL"); + } + console.log("PASS"); + } + expect_exact: [ + " switch (42) {", + " case null:", + ' console.log("FAIL");', + " }", + "", + ' console.log("PASS");', + ] + expect_stdout: "PASS" +} + +tabs: { + beautify = { + beautify: true, + indent_start: "\t", + indent_level: "\t", + } + input: { + switch (42) { + case null: + console.log("FAIL"); + } + console.log("PASS"); + } + expect_exact: [ + "\tswitch (42) {", + "\tcase null:", + '\t\tconsole.log("FAIL");', + "\t}", + "", + '\tconsole.log("PASS");', + ] + expect_stdout: "PASS" +} + +mixed: { + beautify = { + beautify: true, + indent_start: "\n", + indent_level: " \t", + } + input: { + switch (42) { + case null: + console.log("FAIL"); + } + console.log("PASS"); + } + expect_exact: [ + "", + "switch (42) {", + "", + " case null:", + "", + ' \tconsole.log("FAIL");', + "", + "}", + "", + "", + 'console.log("PASS");', + ] + expect_stdout: "PASS" +}