Add CodeMirror styles for basic

This commit is contained in:
Joshua Bell 2013-05-06 23:16:18 -04:00
parent 202bef087a
commit d24f3cd3a6
3 changed files with 268 additions and 1 deletions

View File

@ -24,7 +24,6 @@ You can run your basic programs from the command line (with only basic text inpu
To Do
-----
* Upload the CodeMirror styles
* Snapshot and/or link sensibly to the polyfills
* Implement DOS functionality for consoles

46
cm2/mode/basic/basic.css Normal file
View File

@ -0,0 +1,46 @@
.cm-s-default span.cm-basic-statement {
color: #00007f;
}
.cm-s-default span.cm-basic-unsupported {
color: #00007f;
background-color: #ff7f7f
}
.cm-s-default span.cm-basic-function {
color: teal;
}
.cm-s-default span.cm-basic-identifier {
color: #7f7f00;
}
.cm-s-default span.cm-basic-string {
color: #007f00;
}
.cm-s-default span.cm-basic-number {
color: #0000ff;
}
.cm-s-default span.cm-basic-operator {
color: #7f007f;
}
.cm-s-default span.cm-basic-separator {
color: #7f7f7f;
}
.cm-s-default span.cm-basic-linenumber {
color: orange;
}
.cm-s-default span.cm-basic-comment {
color: #cc00ff;
font-style: italic;
}
.cm-s-default span.cm-basic-error {
color: black;
background-color: red;
}

222
cm2/mode/basic/basic.js Normal file
View File

@ -0,0 +1,222 @@
// Really just a lexer
CodeMirror.defineMode('basic', function(config, parserConfig) {
var STATEMENT = 'basic-statement',
OPERATOR = 'basic-operator',
FUNCTION = 'basic-function',
UNSUPPORTED = 'basic-unsupported';
var reserved = {
"ABS": FUNCTION,
"AND": OPERATOR,
"ASC": FUNCTION,
"ATN": FUNCTION,
"AT": STATEMENT,
"CALL": STATEMENT,
"CHR$": FUNCTION,
"CLEAR": STATEMENT,
"COLOR=": STATEMENT,
"CONT": UNSUPPORTED,
"COS": FUNCTION,
"DATA": STATEMENT,
"DEF": STATEMENT,
"DEL": UNSUPPORTED,
"DIM": STATEMENT,
"DRAW": UNSUPPORTED,
"END": STATEMENT,
"EXP": FUNCTION,
"FLASH": STATEMENT,
"FN": STATEMENT,
"FOR": STATEMENT,
"FRE": FUNCTION,
"GET": STATEMENT,
"GOSUB": STATEMENT,
"GOTO": STATEMENT,
"GR": STATEMENT,
"HCOLOR=": STATEMENT,
"HGR2": STATEMENT,
"HGR": STATEMENT,
"HIMEM:": UNSUPPORTED,
"HLIN": STATEMENT,
"HOME": STATEMENT,
"HPLOT": STATEMENT,
"HTAB": STATEMENT,
"IF": STATEMENT,
"IN#": UNSUPPORTED,
"INPUT": STATEMENT,
"INT": FUNCTION,
"INVERSE": STATEMENT,
"LEFT$": FUNCTION,
"LEN": FUNCTION,
"LET": STATEMENT,
"LIST": UNSUPPORTED,
"LOAD": UNSUPPORTED,
"LOG": FUNCTION,
"LOMEM:": UNSUPPORTED,
"MID$": FUNCTION,
"NEW": UNSUPPORTED,
"NEXT": STATEMENT,
"NORMAL": STATEMENT,
"NOTRACE": STATEMENT,
"NOT": OPERATOR,
"ONERR": STATEMENT,
"ON": STATEMENT,
"OR": OPERATOR,
"PDL": FUNCTION,
"PEEK": FUNCTION,
"PLOT": STATEMENT,
"POKE": STATEMENT,
"POP": STATEMENT,
"POS": FUNCTION,
"PRINT": STATEMENT,
"PR#": STATEMENT,
"READ": STATEMENT,
"RECALL": UNSUPPORTED,
"REM": STATEMENT,
"RESTORE": STATEMENT,
"RESUME": STATEMENT,
"RETURN": STATEMENT,
"RIGHT$": FUNCTION,
"RND": FUNCTION,
"ROT=": UNSUPPORTED,
"RUN": UNSUPPORTED,
"SAVE": UNSUPPORTED,
"SCALE=": UNSUPPORTED,
"SCRN": FUNCTION,
"SGN": FUNCTION,
"SHLOAD": UNSUPPORTED,
"SIN": FUNCTION,
"SPC": FUNCTION,
"SPEED=": STATEMENT,
"SQR": FUNCTION,
"STEP": STATEMENT,
"STOP": STATEMENT,
"STORE": UNSUPPORTED,
"STR$": FUNCTION,
"TAB": FUNCTION,
"TAN": FUNCTION,
"TEXT": STATEMENT,
"THEN": STATEMENT,
"TO": STATEMENT,
"TRACE": STATEMENT,
"USR": FUNCTION,
"VAL": FUNCTION,
"VLIN": STATEMENT,
"VTAB": STATEMENT,
"WAIT": UNSUPPORTED,
"XDRAW": UNSUPPORTED,
"&": UNSUPPORTED,
"?": STATEMENT
};
var reservedKeys = (function() {
// Need longer stems first: ATN/AT, ONERR/ON, NOTRACE/NOT
var keys = [], name;
for (name in reserved) {
if (Object.prototype.hasOwnProperty.call(reserved, name)) {
keys.push(name);
}
}
keys.sort();
keys.reverse();
return keys;
} ());
// states are 'normal' and 'comment'
return {
startState: function() {
return {
state: 'normal'
};
},
token: function(stream, state) {
var name, i;
if (state.state === 'normal') {
if (stream.eatSpace()) {
return null;
}
else if (/[0-9.]/.test(stream.peek())) {
stream.eatWhile(/[0-9]/);
if (stream.peek() === '.') {
stream.next();
stream.eatWhile(/[0-9]/);
}
if (/[eE]/.test(stream.peek())) {
stream.next();
stream.eatWhile(/[ \u00a0]/);
if (stream.peek() === '-' || stream.peek() === '+') {
stream.next();
}
stream.eatWhile(/[ \u00a0]/);
stream.eatWhile(/[0-9]/);
}
return 'basic-number';
}
else if (stream.peek() === '"') {
stream.next();
while (!stream.eol()) {
if (stream.next() === '"') {
break;
}
}
return 'basic-string';
}
else if (/[;=<>+\-*\/\^(),]/.test(stream.peek())) {
stream.next();
return 'basic-operator';
}
else if (stream.peek() === ':') {
stream.next();
return 'basic-separator';
}
else if (stream.match('REM', true, true)) {
stream.eatWhile(/[ \u00a0]/);
if (!stream.eol()) {
state.state = 'comment';
}
return 'basic-statement';
}
// TODO: Applesoft-style space ignoring within reserved words
for (i = 0; i < reservedKeys.length; i += 1) {
name = reservedKeys[i];
if (stream.match(name, true, true)) {
return reserved[name];
}
}
if (/[A-Za-z]/.test(stream.peek())) {
stream.next();
stream.eatWhile(/[A-Za-z0-9]/);
if (stream.peek() === '$' || stream.peek() === '%') {
stream.next();
}
return 'basic-identifier';
}
stream.next();
return 'basic-error';
}
else if (state.state === 'comment') {
while (!stream.eol()) {
stream.next();
}
state.state = 'normal';
return 'basic-comment';
}
else {
throw 'WTF!?';
}
}
};
});
CodeMirror.defineMIME("text/x-basic", "basic");
CodeMirror.defineMIME("text/x-applesoft", "basic");