【发布时间】:2015-12-26 20:08:28
【问题描述】:
我有这段代码可以将较长的行分成等长的字符串数组来保留单词,它还考虑了[[u;#fff;]some text] 之类的格式,它拆分了文本,因此每个字符串都可以独立地转换为 html:
var format_re = /\[\[([!gbiuso]*;[^;\]]*;[^;\]]*(?:;|[^\]()]*);?[^\]]*)\]([^\]]*\\\][^\]]*|[^\]]*|[^\[]*\[[^\]]*)\]?/gi;
var format_begin_re = /(\[\[[!gbiuso]*;[^;]*;[^\]]*\])/i;
var format_last_re = /\[\[[!gbiuso]*;[^;]*;[^\]]*\]?$/i;
$.terminal.split_equal = function(str, length, words) {
var formatting = false;
var in_text = false;
var prev_format = '';
var result = [];
// add format text as 5th paramter to formatting it's used for
// data attribute in format function
var array = str.replace(format_re, function(_, format, text) {
var semicolons = format.match(/;/g).length;
// missing semicolons
if (semicolons == 2) {
semicolons = ';;';
} else if (semicolons == 3) {
semicolons = ';';
} else {
semicolons = '';
}
// return '[[' + format + ']' + text + ']';
// closing braket will break formatting so we need to escape
// those using html entity equvalent
return '[[' + format + semicolons +
text.replace(/\\\]/g, ']').replace(/\n/g, '\\n') + ']' +
text + ']';
}).split(/\n/g);
for (var i = 0, len = array.length; i < len; ++i) {
if (array[i] === '') {
result.push('');
continue;
}
var line = array[i];
var first_index = 0;
var count = 0;
var space = -1;
for (var j=0, jlen=line.length; j<jlen; ++j) {
if (line[j] === '[' && line[j+1] === '[') {
formatting = true;
} else if (formatting && line[j] === ']') {
if (in_text) {
formatting = false;
in_text = false;
} else {
in_text = true;
}
} else if ((formatting && in_text) || !formatting) {
if (line[j] === '&') { // treat entity as one character
var m = line.substring(j).match(/^(&[^;]+;)/);
if (!m) {
// should never happen if used by terminal,
// because it always calls $.terminal.encode
// before this function
throw new Error("Unclosed html entity in line " +
(i+1) + ' at char ' + (j+1));
}
j+=m[1].length-2; // because continue adds 1 to j
// if entity is at the end there is no next loop
// issue #77
if (j === jlen-1) {
result.push(output + m[1]);
}
continue;
} else if (line[j] === ']' && line[j-1] === '\\') {
// escape \] counts as one character
--count;
} else {
++count;
}
}
function is_space() {
return line.substring(j-6, j) == ' ' ||
line.substring(j-1, j) == ' ';
}
if (is_space() && ((formatting && in_text) || !formatting)) {
space = j;
}
if ((count === length || j === jlen-1) &&
((formatting && in_text) || !formatting)) {
var output;
var after = line.substring(space, j+length+1);
var text = $('<span>' + after + '</span>').text();
var can_break = text.match(/\s/);
if (words && space != -1 && j !== jlen-1 && can_break) {
// get text to last space
output = line.substring(first_index, space);
j = space-1;
space = -1;
} else {
output = line.substring(first_index, j+1);
}
if (words) {
output = output.replace(/^( |\s)+|( |\s)+$/g, '');
}
first_index = j+1;
count = 0;
if (prev_format) {
output = prev_format + output;
if (output.match(']')) {
prev_format = '';
}
}
// Fix output if formatting not closed
var matched = output.match(format_re);
if (matched) {
var last = matched[matched.length-1];
if (last[last.length-1] !== ']') {
prev_format = last.match(format_begin_re)[1];
output += ']';
} else if (output.match(format_last_re)) {
var line_len = output.length;
// why this line ???
//var f_len = line_len-last[last.length-1].length;
output = output.replace(format_last_re, '');
prev_format = last.match(format_begin_re)[1];
}
}
result.push(output);
}
}
}
return result;
};
它几乎可以正常工作,但有些行比它应该的要短:
is cracker.The term
在这个FIDDLE 中,当您剥离格式并选中复选框时,它可以正常工作。我为此工作了几个小时,不知道为什么这条线会更短,非常感谢任何帮助。
【问题讨论】:
-
如果
text在下一行换行,[[u;#fff;]some text]会发生什么?你会重复像'[[u;#fff;]some]', '[[u;#fff;]text]'这样的格式吗? -
@WouterHuysentruit 是的。
-
@Valijon 你用过小提琴jsfiddle.net/bjrdamgg/2吗?您需要包含 jQuery 和 jQuery 终端。
-
Chrome 可以,FF 不行
-
是否需要支持嵌套格式
[[u]like [[#fff]this] example]?
标签: javascript jquery