Index: branches/5.3.x/core/admin_templates/incs/code_mirror/mode/xml/xml.js =================================================================== diff -u -N -r15690 -r15914 --- branches/5.3.x/core/admin_templates/incs/code_mirror/mode/xml/xml.js (.../xml.js) (revision 15690) +++ branches/5.3.x/core/admin_templates/incs/code_mirror/mode/xml/xml.js (.../xml.js) (revision 15914) @@ -1,5 +1,7 @@ CodeMirror.defineMode("xml", function(config, parserConfig) { var indentUnit = config.indentUnit; + var multilineTagIndentFactor = parserConfig.multilineTagIndentFactor || 1; + var Kludges = parserConfig.htmlMode ? { autoSelfClosers: {'area': true, 'base': true, 'br': true, 'col': true, 'command': true, 'embed': true, 'frame': true, 'hr': true, 'img': true, 'input': true, @@ -56,20 +58,19 @@ if (stream.eat("[")) { if (stream.match("CDATA[")) return chain(inBlock("atom", "]]>")); else return null; - } - else if (stream.match("--")) return chain(inBlock("comment", "-->")); - else if (stream.match("DOCTYPE", true, true)) { + } else if (stream.match("--")) { + return chain(inBlock("comment", "-->")); + } else if (stream.match("DOCTYPE", true, true)) { stream.eatWhile(/[\w\._\-]/); return chain(doctype(1)); + } else { + return null; } - else return null; - } - else if (stream.eat("?")) { + } else if (stream.eat("?")) { stream.eatWhile(/[\w\._\-]/); state.tokenize = inBlock("meta", "?>"); return "meta"; - } - else { + } else { var isClose = stream.eat("/"); tagName = ""; var c; @@ -79,21 +80,19 @@ state.tokenize = inTag; return "tag"; } - } - else if (ch == "&") { + } else if (ch == "&") { var ok; if (stream.eat("#")) { if (stream.eat("x")) { - ok = stream.eatWhile(/[a-fA-F\d]/) && stream.eat(";"); + ok = stream.eatWhile(/[a-fA-F\d]/) && stream.eat(";"); } else { ok = stream.eatWhile(/[\d]/) && stream.eat(";"); } } else { ok = stream.eatWhile(/[\w\.\-:]/) && stream.eat(";"); } return ok ? "atom" : "error"; - } - else { + } else { stream.eatWhile(/[^&<]/); return null; } @@ -105,16 +104,15 @@ state.tokenize = inText; type = ch == ">" ? "endTag" : "selfcloseTag"; return "tag"; - } - else if (ch == "=") { + } else if (ch == "=") { type = "equals"; return null; - } - else if (/[\'\"]/.test(ch)) { + } else if (ch == "<") { + return "error"; + } else if (/[\'\"]/.test(ch)) { state.tokenize = inAttribute(ch); return state.tokenize(stream, state); - } - else { + } else { stream.eatWhile(/[^\s\u00a0=<>\"\']/); return "word"; } @@ -165,7 +163,7 @@ }; } - var curState, setStyle; + var curState, curStream, setStyle; function pass() { for (var i = arguments.length - 1; i >= 0; i--) curState.cc.push(arguments[i]); } @@ -191,6 +189,7 @@ function element(type) { if (type == "openTag") { curState.tagName = tagName; + curState.tagStart = curStream.column(); return cont(attributes, endtag(curState.startOfLine)); } else if (type == "closeTag") { var err = false; @@ -212,7 +211,7 @@ function endtag(startOfLine) { return function(type) { var tagName = curState.tagName; - curState.tagName = null; + curState.tagName = curState.tagStart = null; if (type == "selfcloseTag" || (type == "endTag" && Kludges.autoSelfClosers.hasOwnProperty(tagName.toLowerCase()))) { maybePopContext(tagName.toLowerCase()); @@ -274,11 +273,11 @@ return { startState: function() { - return {tokenize: inText, cc: [], indented: 0, startOfLine: true, tagName: null, context: null}; + return {tokenize: inText, cc: [], indented: 0, startOfLine: true, tagName: null, tagStart: null, context: null}; }, token: function(stream, state) { - if (stream.sol()) { + if (!state.tagName && stream.sol()) { state.startOfLine = true; state.indented = stream.indentation(); } @@ -288,7 +287,7 @@ var style = state.tokenize(stream, state); state.type = type; if ((style || type) && style != "comment") { - curState = state; + curState = state; curStream = stream; while (true) { var comb = state.cc.pop() || element; if (comb(type || style)) break; @@ -303,6 +302,7 @@ if ((state.tokenize != inTag && state.tokenize != inText) || context && context.noIndent) return fullLine ? fullLine.match(/^(\s*)/)[0].length : 0; + if (state.tagName) return state.tagStart + indentUnit * multilineTagIndentFactor; if (alignCDATA && /", configuration: parserConfig.htmlMode ? "html" : "xml" };