improve CSS and HTML auto indent

This commit is contained in:
Fabian Jakobs 2010-04-20 12:06:47 +02:00
commit ba025f3e87
10 changed files with 132 additions and 19 deletions

View file

@ -4,3 +4,20 @@ ace.mode.Css = function() {
this.$tokenizer = new ace.Tokenizer(new ace.mode.CssHighlightRules().getRules());
};
ace.inherits(ace.mode.Css, ace.mode.Text);
ace.mode.Css.prototype.getNextLineIndent = function(line, state, tab) {
var indent = this.$getIndent(line);
// ignore braces in comments
var tokens = this.$tokenizer.getLineTokens(line, state).tokens;
if (tokens.length && tokens[tokens.length-1].type == "comment") {
return indent;
}
var match = line.match(/^.*\{\s*$/);
if (match) {
indent += tab;
}
return indent;
};

View file

@ -141,6 +141,12 @@ ace.mode.CssHighlightRules = function() {
}, {
token : "number", // hex3 color
regex : "#[a-fA-F0-9]{3}"
}, {
token : "lparen",
regex : "\{"
}, {
token : "rparen",
regex : "\}"
}, {
token : function(value) {
if (properties[value.toLowerCase()]) {

View file

@ -4,6 +4,7 @@ ace.mode.Html = function() {
this.$tokenizer = new ace.Tokenizer(new ace.mode.HtmlHighlightRules().getRules());
this._js = new ace.mode.JavaScript();
this._css = new ace.mode.Css();
};
ace.inherits(ace.mode.Html, ace.mode.Text);
@ -13,6 +14,11 @@ ace.mode.Html.prototype.toggleCommentLines = function(doc, range, state) {
return this._js.toggleCommentLines(doc, range, state);
}
var split = state.split("css-");
if (!split[0] && split[1]) {
return this._css.toggleCommentLines(doc, range, state);
}
return 0;
};
@ -22,5 +28,10 @@ ace.mode.Html.prototype.getNextLineIndent = function(line, state, tab) {
return this._js.getNextLineIndent(line, split[1], tab);
}
var split = state.split("css-");
if (!split[0] && split[1]) {
return this._css.getNextLineIndent(line, split[1], tab);
}
return "";
};

View file

@ -14,28 +14,22 @@ ace.mode.JavaScript.prototype.toggleCommentLines = function(doc, range, state) {
};
ace.mode.JavaScript.prototype.getNextLineIndent = function(line, state, tab) {
var indent = this.$getIndent(line);
if (state == "start") {
var re = /^(\s*).*[\{\(\[]\s*$/;
var match = line.match(re);
var match = line.match(/^.*[\{\(\[]\s*$/);
if (match) {
return (match[1] || "") + tab;
indent += tab;
}
} else if (state == "doc-comment") {
var re = /^(\s*)(\/?)\*.*$/;
var match = line.match(re);
var match = line.match(/^\s*(\/?)\*/);
if (match) {
var indent = match[1];
if (match[2]) {
if (match[1]) {
indent += " ";
}
return indent + "* ";
indent += "* ";
}
}
var match = line.match(/^(\s+).*$/);
if (match) {
return match[1];
}
return "";
return indent;
};

View file

@ -74,11 +74,11 @@ ace.mode.JavaScriptHighlightRules = function() {
},
regex : "[a-zA-Z_][a-zA-Z0-9_]*\\b"
}, {
token : function(value) {
// return parens[value];
return "text";
},
regex : "[\\[\\]\\(\\)\\{\\}]"
token : "lparen",
regex : "[\\[\\(\\{]"
}, {
token : "rparen",
regex : "[\\]\\)\\}]"
}, {
token : "text",
regex : "\\s+"

View file

@ -19,5 +19,14 @@ ace.mode.Text.prototype.toggleCommentLines = function(doc, range, state) {
};
ace.mode.Text.prototype.getNextLineIndent = function(line, state, tab) {
return "";
};
ace.mode.Text.prototype.$getIndent = function(line) {
var match = line.match(/^(\s+)/);
if (match) {
return match[1];
}
return "";
};

33
test/mode/CssTest.js Normal file
View file

@ -0,0 +1,33 @@
var CssTest = new TestCase("mode.CssTest", {
setUp : function() {
this.mode = new ace.mode.Css();
},
"test: toggle comment lines should not do anything" : function() {
var doc = new ace.TextDocument([" abc", "cde", "fg"].join("\n"));
var range = {
start: {row: 0, column: 3},
end: {row: 1, column: 1}
};
var comment = this.mode.toggleCommentLines(doc, range, "start");
assertEquals([" abc", "cde", "fg"].join("\n"), doc.toString());
},
"test: lines should keep indentation" : function() {
assertEquals(" ", this.mode.getNextLineIndent(" abc", "start", " "));
assertEquals("\t", this.mode.getNextLineIndent("\tabc", "start", " "));
},
"test: new line after { should increase indent" : function() {
assertEquals(" ", this.mode.getNextLineIndent(" abc{", "start", " "));
assertEquals("\t ", this.mode.getNextLineIndent("\tabc { ", "start", " "));
},
"test: no indent increase after { in a comment" : function() {
assertEquals(" ", this.mode.getNextLineIndent(" /*{", "start", " "));
}
});

View file

@ -24,5 +24,14 @@ var CssTest = new TestCase("mode.CssTest", {
assertEquals(1, tokens.length);
assertEquals("number", tokens[0].type);
},
"test: tokenize parens" : function() {
var tokens = this.tokenizer.getLineTokens("{()}", "start").tokens;
assertEquals(3, tokens.length);
assertEquals("lparen", tokens[0].type);
assertEquals("text", tokens[1].type);
assertEquals("rparen", tokens[2].type);
}
});

View file

@ -37,5 +37,16 @@ var JavaScriptTokenizerTest = new TestCase("mode.JavaScriptTokenizerTest", {
assertEquals("doc-comment", tokens[0].type);
assertEquals("doc-comment-tag", tokens[1].type);
assertEquals("doc-comment", tokens[2].type);
},
"test: tokenize parens" : function() {
var line = "[{( )}]";
var tokens = this.tokenizer.getLineTokens(line, "start").tokens;
assertEquals(3, tokens.length);
assertEquals("lparen", tokens[0].type);
assertEquals("text", tokens[1].type);
assertEquals("rparen", tokens[2].type);
}
});

23
test/mode/TextTest.js Normal file
View file

@ -0,0 +1,23 @@
var TextTest = new TestCase("mode.TextTest", {
setUp : function() {
this.mode = new ace.mode.Text();
},
"test: toggle comment lines should not do anything" : function() {
var doc = new ace.TextDocument([" abc", "cde", "fg"].join("\n"));
var range = {
start: {row: 0, column: 3},
end: {row: 1, column: 1}
};
var comment = this.mode.toggleCommentLines(doc, range, "start");
assertEquals([" abc", "cde", "fg"].join("\n"), doc.toString());
},
"text: lines should not be indented" : function() {
assertEquals("", this.mode.getNextLineIndent(" abc", " "));
}
});