417 changes: 263 additions & 154 deletions keymap/vim.js

Large diffs are not rendered by default.

36 changes: 21 additions & 15 deletions lib/codemirror.js
Original file line number Diff line number Diff line change
Expand Up @@ -230,6 +230,7 @@ window.CodeMirror = (function() {
var off = eltOffset(lineSpace);
return coordsChar(coords.x - off.left, coords.y - off.top);
},
defaultTextHeight: function() { return textHeight(); },
markText: operation(markText),
setBookmark: setBookmark,
findMarksAt: findMarksAt,
Expand Down Expand Up @@ -344,6 +345,11 @@ window.CodeMirror = (function() {
return {x: scroller.scrollLeft, y: scrollbar.scrollTop,
height: scrollbar.scrollHeight, width: scroller.scrollWidth};
},
scrollIntoView: function(pos) {
var coords = localCoords(pos ? clipPos(pos) : sel.inverted ? sel.from : sel.to);
scrollIntoView(coords.x, coords.y, coords.x, coords.yBot);
},

setSize: function(width, height) {
function interpret(val) {
val = String(val);
Expand Down Expand Up @@ -393,7 +399,7 @@ window.CodeMirror = (function() {
}

function onScrollBar(e) {
if (scrollbar.scrollTop != lastScrollTop) {
if (Math.abs(scrollbar.scrollTop - lastScrollTop) > 1) {
lastScrollTop = scroller.scrollTop = scrollbar.scrollTop;
updateDisplay([]);
}
Expand All @@ -402,7 +408,7 @@ window.CodeMirror = (function() {
function onScrollMain(e) {
if (options.fixedGutter && gutter.style.left != scroller.scrollLeft + "px")
gutter.style.left = scroller.scrollLeft + "px";
if (scroller.scrollTop != lastScrollTop) {
if (Math.abs(scroller.scrollTop - lastScrollTop) > 1) {
lastScrollTop = scroller.scrollTop;
if (scrollbar.scrollTop != lastScrollTop)
scrollbar.scrollTop = lastScrollTop;
Expand Down Expand Up @@ -635,7 +641,7 @@ window.CodeMirror = (function() {
if (handled) {
e_preventDefault(e);
restartBlink();
if (ie) { e.oldKeyCode = e.keyCode; e.keyCode = 0; }
if (ie_lt9) { e.oldKeyCode = e.keyCode; e.keyCode = 0; }
}
return handled;
}
Expand Down Expand Up @@ -2172,7 +2178,7 @@ window.CodeMirror = (function() {
keyMap.emacsy = {
"Ctrl-F": "goCharRight", "Ctrl-B": "goCharLeft", "Ctrl-P": "goLineUp", "Ctrl-N": "goLineDown",
"Alt-F": "goWordRight", "Alt-B": "goWordLeft", "Ctrl-A": "goLineStart", "Ctrl-E": "goLineEnd",
"Ctrl-V": "goPageUp", "Shift-Ctrl-V": "goPageDown", "Ctrl-D": "delCharRight", "Ctrl-H": "delCharLeft",
"Ctrl-V": "goPageDown", "Shift-Ctrl-V": "goPageUp", "Ctrl-D": "delCharRight", "Ctrl-H": "delCharLeft",
"Alt-D": "delWordRight", "Alt-Backspace": "delWordLeft", "Ctrl-K": "killLine", "Ctrl-T": "transposeChars"
};

Expand Down Expand Up @@ -2230,15 +2236,13 @@ window.CodeMirror = (function() {
if (textarea.form) {
// Deplorable hack to make the submit method do the right thing.
var rmSubmit = connect(textarea.form, "submit", save, true);
if (typeof textarea.form.submit == "function") {
var realSubmit = textarea.form.submit;
textarea.form.submit = function wrappedSubmit() {
save();
textarea.form.submit = realSubmit;
textarea.form.submit();
textarea.form.submit = wrappedSubmit;
};
}
var realSubmit = textarea.form.submit;
textarea.form.submit = function wrappedSubmit() {
save();
textarea.form.submit = realSubmit;
textarea.form.submit();
textarea.form.submit = wrappedSubmit;
};
}

textarea.style.display = "none";
Expand Down Expand Up @@ -3100,8 +3104,10 @@ window.CodeMirror = (function() {
if (collection[i] == elt) return i;
return -1;
}
var nonASCIISingleCaseWordChar = /[\u3040-\u309f\u30a0-\u30ff\u3400-\u4db5\u4e00-\u9fcc]/;
function isWordChar(ch) {
return /\w/.test(ch) || ch.toUpperCase() != ch.toLowerCase() || /[\u4E00-\u9FA5]/.test(ch);
return /\w/.test(ch) || ch > "\x80" &&
(ch.toUpperCase() != ch.toLowerCase() || nonASCIISingleCaseWordChar.test(ch));
}

// See if "".split is the broken IE version, if so, provide an
Expand Down Expand Up @@ -3157,7 +3163,7 @@ window.CodeMirror = (function() {
for (var i = 1; i <= 12; i++) keyNames[i + 111] = keyNames[i + 63235] = "F" + i;
})();

CodeMirror.version = "2.35";
CodeMirror.version = "2.36";

return CodeMirror;
})();
36 changes: 36 additions & 0 deletions lib/util/continuecomment.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
(function() {
var modes = ["clike", "css", "javascript"];
for (var i = 0; i < modes.length; ++i)
CodeMirror.extendMode(modes[i], {blockCommentStart: "/*",
blockCommentEnd: "*/",
blockCommentContinue: " * "});

CodeMirror.commands.newlineAndIndentContinueComment = function(cm) {
var pos = cm.getCursor(), token = cm.getTokenAt(pos);
var mode = CodeMirror.innerMode(cm.getMode(), token.state).mode;
var space;

if (token.className == "comment" && mode.blockCommentStart) {
var end = token.string.indexOf(mode.blockCommentEnd);
var full = cm.getRange({line: pos.line, ch: 0}, {line: pos.line, ch: token.end}), found;
if (end != -1 && end == token.string.length - mode.blockCommentEnd.length) {
// Comment ended, don't continue it
} else if (token.string.indexOf(mode.blockCommentStart) == 0) {
space = full.slice(0, token.start);
if (!/^\s*$/.test(space)) {
space = "";
for (var i = 0; i < token.start; ++i) space += " ";
}
} else if ((found = full.indexOf(mode.blockCommentContinue)) != -1 &&
found + mode.blockCommentContinue.length > token.start &&
/^\s*$/.test(full.slice(0, found))) {
space = full.slice(0, found);
}
}

if (space != null)
cm.replaceSelection("\n" + space + mode.blockCommentContinue, "end");
else
cm.execCommand("newlineAndIndent");
};
})();
17 changes: 10 additions & 7 deletions lib/util/formatting.js
Original file line number Diff line number Diff line change
Expand Up @@ -47,13 +47,16 @@

autoFormatLineBreaks: function (text) {
var curPos = 0;
var reLinesSplitter = /(;|\{|\})([^\r\n;])/g;
var nonBreakableBlocks = jsNonBreakableBlocks(text);
var split = this.jsonMode ? function(str) {
return str.replace(/([,{])/g, "$1\n").replace(/}/g, "\n}");
} : function(str) {
return str.replace(/(;|\{|\})([^\r\n;])/g, "$1\n$2");
};
var nonBreakableBlocks = jsNonBreakableBlocks(text), res = "";
if (nonBreakableBlocks != null) {
var res = "";
for (var i = 0; i < nonBreakableBlocks.length; i++) {
if (nonBreakableBlocks[i].start > curPos) { // Break lines till the block
res += text.substring(curPos, nonBreakableBlocks[i].start).replace(reLinesSplitter, "$1\n$2");
res += split(text.substring(curPos, nonBreakableBlocks[i].start));
curPos = nonBreakableBlocks[i].start;
}
if (nonBreakableBlocks[i].start <= curPos
Expand All @@ -63,11 +66,11 @@
}
}
if (curPos < text.length)
res += text.substr(curPos).replace(reLinesSplitter, "$1\n$2");
return res;
res += split(text.substr(curPos));
} else {
return text.replace(reLinesSplitter, "$1\n$2");
res = split(text);
}
return res.replace(/^\n*|\n*$/, "");
}
});

Expand Down
6 changes: 0 additions & 6 deletions lib/util/xml-hint.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,7 @@
cm.setCursor(cursor);
}

// dirty hack for simple-hint to receive getHint event on space
var getTokenAt = editor.getTokenAt;

editor.getTokenAt = function() { return 'disabled'; };
CodeMirror.simpleHint(cm, getHint);

editor.getTokenAt = getTokenAt;
};

var getHint = function(cm) {
Expand Down
2 changes: 1 addition & 1 deletion mode/clike/clike.js
Original file line number Diff line number Diff line change
Expand Up @@ -133,7 +133,7 @@ CodeMirror.defineMode("clike", function(config, parserConfig) {
while (ctx.type == "statement") ctx = popContext(state);
}
else if (curPunc == ctx.type) popContext(state);
else if (ctx.type == "}" || ctx.type == "top" || (ctx.type == "statement" && curPunc == "newstatement"))
else if (((ctx.type == "}" || ctx.type == "top") && curPunc != ';') || (ctx.type == "statement" && curPunc == "newstatement"))
pushContext(state, stream.column(), "statement");
state.startOfLine = false;
return style;
Expand Down
2 changes: 1 addition & 1 deletion mode/gfm/gfm.js
Original file line number Diff line number Diff line change
Expand Up @@ -91,4 +91,4 @@ CodeMirror.defineMode("gfm", function(config, parserConfig) {
fencedCodeBlocks: true
});
return CodeMirror.overlayMode(CodeMirror.getMode(config, "gfmBase"), gfmOverlay);
});
}, "markdown");
2 changes: 1 addition & 1 deletion mode/gfm/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ <h1>CodeMirror: GFM mode</h1>

Underscores_are_allowed_between_words.

## Fenced code blocks (and syntax highlighting... someday)
## Fenced code blocks (and syntax highlighting)

```javascript
for (var i = 0; i &lt; items.length; i++) {
Expand Down
2 changes: 1 addition & 1 deletion mode/htmlmixed/htmlmixed.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ CodeMirror.defineMode("htmlmixed", function(config) {
var close = cur.search(pat), m;
if (close > -1) stream.backUp(cur.length - close);
else if (m = cur.match(/<\/?$/)) {
stream.backUp(cur[0].length);
stream.backUp(cur.length);
if (!stream.match(pat, false)) stream.match(cur[0]);
}
return style;
Expand Down
4 changes: 3 additions & 1 deletion mode/javascript/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
<title>CodeMirror: JavaScript mode</title>
<link rel="stylesheet" href="../../lib/codemirror.css">
<script src="../../lib/codemirror.js"></script>
<script src="../../lib/util/continuecomment.js"></script>
<script src="javascript.js"></script>
<link rel="stylesheet" href="../../doc/docs.css">
<style type="text/css">.CodeMirror {border-top: 1px solid black; border-bottom: 1px solid black;}</style>
Expand Down Expand Up @@ -65,7 +66,8 @@ <h1>CodeMirror: JavaScript mode</h1>
<script>
var editor = CodeMirror.fromTextArea(document.getElementById("code"), {
lineNumbers: true,
matchBrackets: true
matchBrackets: true,
extraKeys: {"Enter": "newlineAndIndentContinueComment"}
});
</script>

Expand Down
4 changes: 3 additions & 1 deletion mode/javascript/javascript.js
Original file line number Diff line number Diff line change
Expand Up @@ -399,7 +399,9 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) {
else return lexical.indented + (closing ? 0 : indentUnit);
},

electricChars: ":{}"
electricChars: ":{}",

jsonMode: jsonMode
};
});

Expand Down
29 changes: 23 additions & 6 deletions mode/mysql/mysql.js
Original file line number Diff line number Diff line change
Expand Up @@ -56,12 +56,13 @@ CodeMirror.defineMode("mysql", function(config) {
curPunc = ch;
return null;
}
else if (ch == "-") {
var ch2 = stream.next();
if (ch2=="-") {
stream.skipToEnd();
return "comment";
}
else if (ch == "-" && stream.eat("-")) {
stream.skipToEnd();
return "comment";
}
else if (ch == "/" && stream.eat("*")) {
state.tokenize = tokenComment;
return state.tokenize(stream, state);
}
else if (operatorChars.test(ch)) {
stream.eatWhile(operatorChars);
Expand Down Expand Up @@ -115,6 +116,22 @@ CodeMirror.defineMode("mysql", function(config) {
};
}

function tokenComment(stream, state) {
for (;;) {
if (stream.skipTo("*")) {
stream.next();
if (stream.eat("/")) {
state.tokenize = tokenBase;
break;
}
} else {
stream.skipToEnd();
break;
}
}
return "comment";
}


function pushContext(state, type, col) {
state.context = {prev: state.context, indent: state.indent, col: col, type: type};
Expand Down
1 change: 1 addition & 0 deletions mode/php/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
<title>CodeMirror: PHP mode</title>
<link rel="stylesheet" href="../../lib/codemirror.css">
<script src="../../lib/codemirror.js"></script>
<script src="../htmlmixed/htmlmixed.js"></script>
<script src="../xml/xml.js"></script>
<script src="../javascript/javascript.js"></script>
<script src="../css/css.js"></script>
Expand Down
46 changes: 13 additions & 33 deletions mode/php/php.js
Original file line number Diff line number Diff line change
Expand Up @@ -50,19 +50,16 @@
};

CodeMirror.defineMode("php", function(config, parserConfig) {
var htmlMode = CodeMirror.getMode(config, {name: "xml", htmlMode: true});
var jsMode = CodeMirror.getMode(config, "javascript");
var cssMode = CodeMirror.getMode(config, "css");
var htmlMode = CodeMirror.getMode(config, "text/html");
var phpMode = CodeMirror.getMode(config, phpConfig);

function dispatch(stream, state) { // TODO open PHP inside text/css
function dispatch(stream, state) {
var isPHP = state.curMode == phpMode;
if (stream.sol() && state.pending != '"') state.pending = null;
if (state.curMode == htmlMode) {
if (!isPHP) {
if (stream.match(/^<\?\w*/)) {
state.curMode = phpMode;
state.curState = state.php;
state.curClose = "?>";
return "meta";
}
if (state.pending == '"') {
Expand All @@ -80,51 +77,33 @@
if (style == "string" && /\"$/.test(cur) && !/\?>/.test(cur)) state.pending = '"';
else state.pending = {end: stream.pos, style: style};
stream.backUp(cur.length - openPHP);
} else if (style == "tag" && stream.current() == ">" && state.curState.context) {
if (/^script$/i.test(state.curState.context.tagName)) {
state.curMode = jsMode;
state.curState = jsMode.startState(htmlMode.indent(state.curState, ""));
state.curClose = /^<\/\s*script\s*>/i;
}
else if (/^style$/i.test(state.curState.context.tagName)) {
state.curMode = cssMode;
state.curState = cssMode.startState(htmlMode.indent(state.curState, ""));
state.curClose = /^<\/\s*style\s*>/i;
}
}
return style;
} else if ((!isPHP || state.php.tokenize == null) &&
stream.match(state.curClose, isPHP)) {
} else if (isPHP && state.php.tokenize == null && stream.match("?>")) {
state.curMode = htmlMode;
state.curState = state.html;
state.curClose = null;
if (isPHP) return "meta";
else return dispatch(stream, state);
return "meta";
} else {
return state.curMode.token(stream, state.curState);
return phpMode.token(stream, state.curState);
}
}

return {
startState: function() {
var html = htmlMode.startState();
var html = CodeMirror.startState(htmlMode), php = CodeMirror.startState(phpMode);
return {html: html,
php: phpMode.startState(),
php: php,
curMode: parserConfig.startOpen ? phpMode : htmlMode,
curState: parserConfig.startOpen ? phpMode.startState() : html,
curClose: parserConfig.startOpen ? /^\?>/ : null,
mode: parserConfig.startOpen ? "php" : "html",
curState: parserConfig.startOpen ? php : html,
pending: null};
},

copyState: function(state) {
var html = state.html, htmlNew = CodeMirror.copyState(htmlMode, html),
php = state.php, phpNew = CodeMirror.copyState(phpMode, php), cur;
if (state.curState == html) cur = htmlNew;
else if (state.curState == php) cur = phpNew;
else cur = CodeMirror.copyState(state.curMode, state.curState);
if (state.curMode == htmlMode) cur = htmlNew;
else cur = phpNew;
return {html: htmlNew, php: phpNew, curMode: state.curMode, curState: cur,
curClose: state.curClose, mode: state.mode,
pending: state.pending};
},

Expand All @@ -141,7 +120,8 @@

innerMode: function(state) { return {state: state.curState, mode: state.curMode}; }
};
}, "xml", "clike", "javascript", "css");
}, "htmlmixed");

CodeMirror.defineMIME("application/x-httpd-php", "php");
CodeMirror.defineMIME("application/x-httpd-php-open", {name: "php", startOpen: true});
CodeMirror.defineMIME("text/x-php", phpConfig);
Expand Down
8 changes: 5 additions & 3 deletions mode/python/python.js
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ CodeMirror.defineMode("python", function(conf, parserConf) {
var singleline = delimiter.length == 1;
var OUTCLASS = 'string';

return function tokenString(stream, state) {
function tokenString(stream, state) {
while (!stream.eol()) {
stream.eatWhile(/[^'"\\]/);
if (stream.eat('\\')) {
Expand All @@ -183,7 +183,9 @@ CodeMirror.defineMode("python", function(conf, parserConf) {
}
}
return OUTCLASS;
};
}
tokenString.isString = true;
return tokenString;
}

function indent(stream, state, type) {
Expand Down Expand Up @@ -325,7 +327,7 @@ CodeMirror.defineMode("python", function(conf, parserConf) {

indent: function(state, textAfter) {
if (state.tokenize != tokenBase) {
return 0;
return state.tokenize.isString ? CodeMirror.Pass : 0;
}

return state.scopes[0].offset;
Expand Down
8 changes: 5 additions & 3 deletions mode/xml/xml.js
Original file line number Diff line number Diff line change
Expand Up @@ -70,11 +70,12 @@ CodeMirror.defineMode("xml", function(config, parserConfig) {
return "meta";
}
else {
type = stream.eat("/") ? "closeTag" : "openTag";
stream.eatSpace();
var isClose = stream.eat("/");
tagName = "";
var c;
while ((c = stream.eat(/[^\s\u00a0=<>\"\'\/?]/))) tagName += c;
if (!tagName) return "error";
type = isClose ? "closeTag" : "openTag";
state.tokenize = inTag;
return "tag";
}
Expand Down Expand Up @@ -114,7 +115,7 @@ CodeMirror.defineMode("xml", function(config, parserConfig) {
return state.tokenize(stream, state);
}
else {
stream.eatWhile(/[^\s\u00a0=<>\"\'\/?]/);
stream.eatWhile(/[^\s\u00a0=<>\"\']/);
return "word";
}
}
Expand Down Expand Up @@ -255,6 +256,7 @@ CodeMirror.defineMode("xml", function(config, parserConfig) {
function attribute(type) {
if (type == "equals") return cont(attvalue, attributes);
if (!Kludges.allowMissing) setStyle = "error";
else if (type == "word") setStyle = "attribute";
return (type == "endTag" || type == "selfcloseTag") ? pass() : cont();
}
function attvalue(type) {
Expand Down
39 changes: 39 additions & 0 deletions mode/z80/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>CodeMirror: Z80 assembly mode</title>
<link rel="stylesheet" href="../../lib/codemirror.css">
<script src="../../lib/codemirror.js"></script>
<script src="z80.js"></script>
<link rel="stylesheet" href="../../doc/docs.css">
<style type="text/css">.CodeMirror {border-top: 1px solid black; border-bottom: 1px solid black;}</style>
</head>
<body>
<h1>CodeMirror: Z80 assembly mode</h1>

<div><textarea id="code" name="code">
#include "ti83plus.inc"
#define progStart $9D95
.org progStart-2
.db $BB,$6D
bcall(_ClrLCDFull)
ld HL, 0
ld (PenCol), HL
ld HL, Message
bcall(_PutS) ; Displays the string
bcall(_NewLine)
ret
Message:
.db "Hello world!",0
</textarea></div>

<script>
var editor = CodeMirror.fromTextArea(document.getElementById("code"), {
lineNumbers: true
});
</script>

<p><strong>MIME type defined:</strong> <code>text/x-z80</code>.</p>
</body>
</html>
113 changes: 113 additions & 0 deletions mode/z80/z80.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
CodeMirror.defineMode('z80', function()
{
var keywords1 = /^(exx?|(ld|cp|in)([di]r?)?|pop|push|ad[cd]|cpl|daa|dec|inc|neg|sbc|sub|and|bit|[cs]cf|x?or|res|set|r[lr]c?a?|r[lr]d|s[lr]a|srl|djnz|nop|rst|[de]i|halt|im|ot[di]r|out[di]?)\b/i;
var keywords2 = /^(call|j[pr]|ret[in]?)\b/i;
var keywords3 = /^b_?(call|jump)\b/i;
var variables1 = /^(af?|bc?|c|de?|e|hl?|l|i[xy]?|r|sp)\b/i;
var variables2 = /^(n?[zc]|p[oe]?|m)\b/i;
var errors = /^([hl][xy]|i[xy][hl]|slia|sll)\b/i;
var numbers = /^([\da-f]+h|[0-7]+o|[01]+b|\d+)\b/i;

return {startState: function()
{
return {context: 0};
}, token: function(stream, state)
{
if (!stream.column())
state.context = 0;

if (stream.eatSpace())
return null;

var w;

if (stream.eatWhile(/\w/))
{
w = stream.current();

if (stream.indentation())
{
if (state.context == 1 && variables1.test(w))
return 'variable-2';

if (state.context == 2 && variables2.test(w))
return 'variable-3';

if (keywords1.test(w))
{
state.context = 1;
return 'keyword';
}
else if (keywords2.test(w))
{
state.context = 2;
return 'keyword';
}
else if (keywords3.test(w))
{
state.context = 3;
return 'keyword';
}

if (errors.test(w))
return 'error';
}
else if (numbers.test(w))
{
return 'number';
}
else
{
return null;
}
}
else if (stream.eat(';'))
{
stream.skipToEnd();
return 'comment';
}
else if (stream.eat('"'))
{
while (w = stream.next())
{
if (w == '"')
break;

if (w == '\\')
stream.next();
}

return 'string';
}
else if (stream.eat('\''))
{
if (stream.match(/\\?.'/))
return 'number';
}
else if (stream.eat('.') || stream.sol() && stream.eat('#'))
{
state.context = 4;

if (stream.eatWhile(/\w/))
return 'def';
}
else if (stream.eat('$'))
{
if (stream.eatWhile(/[\da-f]/i))
return 'number';
}
else if (stream.eat('%'))
{
if (stream.eatWhile(/[01]/))
return 'number';
}
else
{
stream.next();
}

return null;
}};
});

CodeMirror.defineMIME("text/x-z80", "z80");
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "codemirror",
"version":"2.35.0",
"version":"2.36.0",
"main": "codemirror.js",
"description": "In-browser code editing made bearable",
"licenses": [{"type": "MIT",
Expand Down
6 changes: 6 additions & 0 deletions theme/ambiance-mobile.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
.CodeMirror .cm-s-ambiance {
-webkit-box-shadow: none;
-moz-box-shadow: none;
-o-box-shadow: none;
box-shadow: none;
}
2 changes: 1 addition & 1 deletion theme/ambiance.css
26 changes: 26 additions & 0 deletions theme/twilight.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
.cm-s-twilight { background: #141414; color: #f7f7f7; } /**/
.cm-s-twilight .CodeMirror-selected { background: #323232 !important; } /**/

.cm-s-twilight .CodeMirror-gutter { background: #222; border-right: 1px solid #aaa; }
.cm-s-twilight .CodeMirror-gutter-text { color: #aaa; }
.cm-s-twilight .CodeMirror-cursor { border-left: 1px solid white !important; }

.cm-s-twilight .cm-keyword { color: #f9ee98; } /**/
.cm-s-twilight .cm-atom { color: #FC0; }
.cm-s-twilight .cm-number { color: #ca7841; } /**/
.cm-s-twilight .cm-def { color: #8DA6CE; }
.cm-s-twilight span.cm-variable-2, .cm-s-twilight span.cm-tag { color: #607392; } /**/
.cm-s-twilight span.cm-variable-3, .cm-s-twilight span.cm-def { color: #607392; } /**/
.cm-s-twilight .cm-operator { color: #cda869; } /**/
.cm-s-twilight .cm-comment { color:#777; font-style:italic; font-weight:normal; } /**/
.cm-s-twilight .cm-string { color:#8f9d6a; font-style:italic; } /**/
.cm-s-twilight .cm-string-2 { color:#bd6b18 } /*?*/
.cm-s-twilight .cm-meta { background-color:#141414; color:#f7f7f7; } /*?*/
.cm-s-twilight .cm-error { border-bottom: 1px solid red; }
.cm-s-twilight .cm-builtin { color: #cda869; } /*?*/
.cm-s-twilight .cm-tag { color: #997643; } /**/
.cm-s-twilight .cm-attribute { color: #d6bb6d; } /*?*/
.cm-s-twilight .cm-header { color: #FF6400; }
.cm-s-twilight .cm-hr { color: #AEAEAE; }
.cm-s-twilight .cm-link { color:#ad9361; font-style:italic; font-underline:none; } /**/