如何在 JavaScript 中格式化/整理/美化
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/3913355/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to format/tidy/beautify in JavaScript
提问by Petah
How can I format/tidy/beautify HTML in JavaScript? I have tried doing a search/replace for angle brackets (<
, >
) and indenting accordingly.But of course it does not take into account when the is JS or CSS etc inside the HTML.
如何在 JavaScript 中格式化/整理/美化 HTML?我尝试搜索/替换尖括号 ( <
, >
) 并相应地缩进。但是当然它没有考虑 HTML 中的 JS 或 CSS 等。
The reason I want to do this is I have made a content editor (CMS) which has both WYSIWYG and source code views. The problem the code written by the WYSIWYG editor is normally a single line. So I would like a JavaScript that could format this into a more readable form on demand.
我想这样做的原因是我制作了一个内容编辑器(CMS),它具有所见即所得和源代码视图。WYSIWYG 编辑器编写的代码的问题通常是单行。所以我想要一个可以根据需要将其格式化为更易读的形式的 JavaScript。
Here what I have so far:
这是我到目前为止所拥有的:
function getIndent(level) {
var result = '',
i = level * 4;
if (level < 0) {
throw "Level is below 0";
}
while (i--) {
result += ' ';
}
return result;
}
function style_html(html) {
html = html.trim();
var result = '',
indentLevel = 0,
tokens = html.split(/</);
for (var i = 0, l = tokens.length; i < l; i++) {
var parts = tokens[i].split(/>/);
if (parts.length === 2) {
if (tokens[i][0] === '/') {
indentLevel--;
}
result += getIndent(indentLevel);
if (tokens[i][0] !== '/') {
indentLevel++;
}
if (i > 0) {
result += '<';
}
result += parts[0].trim() + ">\n";
if (parts[1].trim() !== '') {
result += getIndent(indentLevel) + parts[1].trim().replace(/\s+/g, ' ') + "\n";
}
if (parts[0].match(/^(img|hr|br)/)) {
indentLevel--;
}
} else {
result += getIndent(indentLevel) + parts[0] + "\n";
}
}
return result;
}
回答by rickdog
@lovasoa How to format/tidy/beautify in JavaScriptis an excellent solution.
rock-solid, much better than vkBeautify or even CodeMirror (hard to use AMD) and VERY easy
@lovasoa如何在 JavaScript 中格式化/整理/美化是一个很好的解决方案。
坚如磐石,比 vkBeautify 甚至 CodeMirror(难以使用 AMD)好得多,而且非常容易
<script src='http://lovasoa.github.io/tidy-html5/tidy.js'></script>
<script>
options = {
"indent":"auto",
"indent-spaces":2,
"wrap":80,
"markup":true,
"output-xml":false,
"numeric-entities":true,
"quote-marks":true,
"quote-nbsp":false,
"show-body-only":true,
"quote-ampersand":false,
"break-before-br":true,
"uppercase-tags":false,
"uppercase-attributes":false,
"drop-font-tags":true,
"tidy-mark":false
}
var html = document.querySelector("body").outerHTML;
var result = tidy_html5(html, options);
console.log(result);
</script>
回答by michal.jakubeczy
I use this method to format HTML. Simple, but does the job:
我使用这种方法来格式化 HTML。简单,但可以完成工作:
function format(html) {
var tab = '\t';
var result = '';
var indent= '';
html.split(/>\s*</).forEach(function(element) {
if (element.match( /^\/\w/ )) {
indent = indent.substring(tab.length);
}
result += indent + '<' + element + '>\r\n';
if (element.match( /^<?\w[^>]*[^\/]$/ )) {
indent += tab;
}
});
return result.substring(1, result.length-3);
}
回答by nickleefly
You can also use a command line tool if you have node.js install
如果你安装了 node.js,你也可以使用命令行工具
run npm install -g uglify-js
to install uglifyjs globally, check herefor documentation.
运行npm install -g uglify-js
以全局安装 uglifyjs,请在此处查看文档。
Then you can uglify index.min.js -b -o index.js
然后你可以 uglify index.min.js -b -o index.js
回答by Gabriel
I needed something similar and here is my solution, inspired by method provided by michal.jakubeczy. It is slightly complicated in order to preserve formatting within <pre>
tags. Hope this will help someone.
我需要类似的东西,这是我的解决方案,灵感来自 michal.jakubeczy 提供的方法。为了保留<pre>
标签内的格式,它有点复杂。希望这会帮助某人。
function formatHTML(html) {
var indent = '\n';
var tab = '\t';
var i = 0;
var pre = [];
html = html
.replace(new RegExp('<pre>((.|\t|\n|\r)+)?</pre>'), function (x) {
pre.push({ indent: '', tag: x });
return '<--TEMPPRE' + i++ + '/-->'
})
.replace(new RegExp('<[^<>]+>[^<]?', 'g'), function (x) {
var ret;
var tag = /<\/?([^\s/>]+)/.exec(x)[1];
var p = new RegExp('<--TEMPPRE(\d+)/-->').exec(x);
if (p)
pre[p[1]].indent = indent;
if (['area', 'base', 'br', 'col', 'command', 'embed', 'hr', 'img', 'input', 'keygen', 'link', 'menuitem', 'meta', 'param', 'source', 'track', 'wbr'].indexOf(tag) >= 0) // self closing tag
ret = indent + x;
else {
if (x.indexOf('</') < 0) { //open tag
if (x.charAt(x.length - 1) !== '>')
ret = indent + x.substr(0, x.length - 1) + indent + tab + x.substr(x.length - 1, x.length);
else
ret = indent + x;
!p && (indent += tab);
}
else {//close tag
indent = indent.substr(0, indent.length - 1);
if (x.charAt(x.length - 1) !== '>')
ret = indent + x.substr(0, x.length - 1) + indent + x.substr(x.length - 1, x.length);
else
ret = indent + x;
}
}
return ret;
});
for (i = pre.length; i--;) {
html = html.replace('<--TEMPPRE' + i + '/-->', pre[i].tag.replace('<pre>', '<pre>\n').replace('</pre>', pre[i].indent + '</pre>'));
}
return html.charAt(0) === '\n' ? html.substr(1, html.length - 1) : html;
}
function unformatHTML(html) {
var i = 0;
var pre = [];
html = html.replace(new RegExp('<pre>((.|\t|\n|\r)+)?</pre>'), function (x) {
pre.push(x);
return '<--TEMPPRE' + i++ + '/-->'
}).replace(/\n/g, '').replace(/\t/g, '');
for (i = pre.length; i--;) {
html = html.replace('<--TEMPPRE' + i + '/-->', pre[i]);
}
html = html.replace(new RegExp('<pre>\n'), '<pre>').replace(new RegExp('\n\t*</pre>'), '</pre>');
return html;
}
回答by Daniel Mendel
jQuery creator John Resig wrote a fast and lightweight HTML parser in javascript. If you're looking for a solution which you can add directly to your CMS then you could write a simple beautifier using this parser as a base. All you'd need to do is reoutput the elements adding spaces and line breaks as you like, using the built in api:
jQuery 创建者 John Resig用 javascript编写了一个快速且轻量级的HTML 解析器。如果您正在寻找可以直接添加到 CMS 的解决方案,那么您可以使用此解析器作为基础编写一个简单的美化器。您需要做的就是使用内置的api重新输出添加空格和换行符的元素:
HTMLParser(htmlString, {
start: function(tag, attrs, unary) {},
end: function(tag) {},
chars: function(text) {},
comment: function(text) {}
});
An added benefit of this approach is that you could use the same HTMLParser to read HTML back into your WYSIWYG, or otherwise interact with your user's HTML tree. HTMLParser also comes prebuilt with an HTMLtoDOM method.
这种方法的另一个好处是您可以使用相同的 HTMLParser 将 HTML 读回您的所见即所得,或者以其他方式与用户的 HTML 树交互。HTMLParser 还预先构建了一个 HTMLtoDOM 方法。
回答by Paul McMillan
I believe that both chrome and firebug's debugging code display engines are written in JS. That's probably heavier duty than you really want to be messing with though.
相信chrome和firebug的调试代码显示引擎都是JS写的。不过,这可能比你真正想要搞砸的任务更重。
回答by Eric
Writing the htmlon one line would download faster to the browser, so I am not sure I would want it formatted. Maybe an option for a formatted version or an optimized version.
在一行上编写html会更快地下载到浏览器,所以我不确定我是否想要格式化它。也许是格式化版本或优化版本的选项。
As for the question... you could do an ajaxcall after so many actions and send the code to the server to be formatted and shown in a different box on the screen. Basically it would be a real time version of this site, http://infohound.net/tidy/
至于问题......你可以在这么多操作后进行ajax调用,并将代码发送到服务器进行格式化并显示在屏幕上的不同框中。基本上它是这个网站的实时版本,http://infohound.net/tidy/
回答by rickdog
Resig's formatter fails with a very simple test case:
Resig 的格式化程序因一个非常简单的测试用例而失败:
at http://ejohn.org/apps/htmlparser/
在http://ejohn.org/apps/htmlparser/
in the input box enter:
在输入框中输入:
<script src="/files/htmlparser.js"></script>
<script>
var x = 1;
</script>
output box renders:
输出框呈现:
<script src="/files/htmlparser.js"></script>
<script></script>
var x = 1;