Spade

Mini Shell

Directory:~$ /home/lmsyaran/public_html/j3/media/editors/codemirror/mode/mathematica/
Upload File

[Home] [System Details] [Kill Me]
Current File:~$ /home/lmsyaran/public_html/j3/media/editors/codemirror/mode/mathematica/mathematica.js

// CodeMirror, copyright (c) by Marijn Haverbeke and others
// Distributed under an MIT license: https://codemirror.net/LICENSE

// Mathematica mode copyright (c) 2015 by Calin Barbat
// Based on code by Patrick Scheibe (halirutan)
// See:
https://github.com/halirutan/Mathematica-Source-Highlighting/tree/master/src/lang-mma.js

(function(mod) {
  if (typeof exports == "object" && typeof module ==
"object") // CommonJS
    mod(require("../../lib/codemirror"));
  else if (typeof define == "function" && define.amd) //
AMD
    define(["../../lib/codemirror"], mod);
  else // Plain browser env
    mod(CodeMirror);
})(function(CodeMirror) {
"use strict";

CodeMirror.defineMode('mathematica', function(_config,
_parserConfig) {

  // used pattern building blocks
  var Identifier = '[a-zA-Z\\$][a-zA-Z0-9\\$]*';
  var pBase      = "(?:\\d+)";
  var pFloat     = "(?:\\.\\d+|\\d+\\.\\d*|\\d+)";
  var pFloatBase = "(?:\\.\\w+|\\w+\\.\\w*|\\w+)";
  var pPrecision = "(?:`(?:`?"+pFloat+")?)";

  // regular expressions
  var reBaseForm        = new
RegExp('(?:'+pBase+'(?:\\^\\^'+pFloatBase+pPrecision+'?(?:\\*\\^[+-]?\\d+)?))');
  var reFloatForm       = new RegExp('(?:' + pFloat + pPrecision
+ '?(?:\\*\\^[+-]?\\d+)?)');
  var reIdInContext     = new RegExp('(?:`?)(?:' + Identifier +
')(?:`(?:' + Identifier + '))*(?:`?)');

  function tokenBase(stream, state) {
    var ch;

    // get next character
    ch = stream.next();

    // string
    if (ch === '"') {
      state.tokenize = tokenString;
      return state.tokenize(stream, state);
    }

    // comment
    if (ch === '(') {
      if (stream.eat('*')) {
        state.commentLevel++;
        state.tokenize = tokenComment;
        return state.tokenize(stream, state);
      }
    }

    // go back one character
    stream.backUp(1);

    // look for numbers
    // Numbers in a baseform
    if (stream.match(reBaseForm, true, false)) {
      return 'number';
    }

    // Mathematica numbers. Floats (1.2, .2, 1.) can have optionally a
precision (`float) or an accuracy definition
    // (``float). Note: while 1.2` is possible 1.2`` is not. At the end an
exponent (float*^+12) can follow.
    if (stream.match(reFloatForm, true, false)) {
      return 'number';
    }

    /* In[23] and Out[34] */
    if (stream.match(/(?:In|Out)\[[0-9]*\]/, true, false)) {
      return 'atom';
    }

    // usage
    if
(stream.match(/([a-zA-Z\$][a-zA-Z0-9\$]*(?:`[a-zA-Z0-9\$]+)*::usage)/,
true, false)) {
      return 'meta';
    }

    // message
    if
(stream.match(/([a-zA-Z\$][a-zA-Z0-9\$]*(?:`[a-zA-Z0-9\$]+)*::[a-zA-Z\$][a-zA-Z0-9\$]*):?/,
true, false)) {
      return 'string-2';
    }

    // this makes a look-ahead match for something like variable:{_Integer}
    // the match is then forwarded to the mma-patterns tokenizer.
    if
(stream.match(/([a-zA-Z\$][a-zA-Z0-9\$]*\s*:)(?:(?:[a-zA-Z\$][a-zA-Z0-9\$]*)|(?:[^:=>~@\^\&\*\)\[\]'\?,\|])).*/,
true, false)) {
      return 'variable-2';
    }

    // catch variables which are used together with Blank (_),
BlankSequence (__) or BlankNullSequence (___)
    // Cannot start with a number, but can have numbers at any other
position. Examples
    // blub__Integer, a1_, b34_Integer32
    if (stream.match(/[a-zA-Z\$][a-zA-Z0-9\$]*_+[a-zA-Z\$][a-zA-Z0-9\$]*/,
true, false)) {
      return 'variable-2';
    }
    if (stream.match(/[a-zA-Z\$][a-zA-Z0-9\$]*_+/, true, false)) {
      return 'variable-2';
    }
    if (stream.match(/_+[a-zA-Z\$][a-zA-Z0-9\$]*/, true, false)) {
      return 'variable-2';
    }

    // Named characters in Mathematica, like \[Gamma].
    if (stream.match(/\\\[[a-zA-Z\$][a-zA-Z0-9\$]*\]/, true, false)) {
      return 'variable-3';
    }

    // Match all braces separately
    if (stream.match(/(?:\[|\]|{|}|\(|\))/, true, false)) {
      return 'bracket';
    }

    // Catch Slots (#, ##, #3, ##9 and the V10 named slots #name). I have
never seen someone using more than one digit after #, so we match
    // only one.
    if (stream.match(/(?:#[a-zA-Z\$][a-zA-Z0-9\$]*|#+[0-9]?)/, true,
false)) {
      return 'variable-2';
    }

    // Literals like variables, keywords, functions
    if (stream.match(reIdInContext, true, false)) {
      return 'keyword';
    }

    // operators. Note that operators like @@ or /; are matched separately
for each symbol.
    if
(stream.match(/(?:\\|\+|\-|\*|\/|,|;|\.|:|@|~|=|>|<|&|\||_|`|'|\^|\?|!|%)/,
true, false)) {
      return 'operator';
    }

    // everything else is an error
    stream.next(); // advance the stream.
    return 'error';
  }

  function tokenString(stream, state) {
    var next, end = false, escaped = false;
    while ((next = stream.next()) != null) {
      if (next === '"' && !escaped) {
        end = true;
        break;
      }
      escaped = !escaped && next === '\\';
    }
    if (end && !escaped) {
      state.tokenize = tokenBase;
    }
    return 'string';
  };

  function tokenComment(stream, state) {
    var prev, next;
    while(state.commentLevel > 0 && (next = stream.next()) !=
null) {
      if (prev === '(' && next === '*')
state.commentLevel++;
      if (prev === '*' && next === ')')
state.commentLevel--;
      prev = next;
    }
    if (state.commentLevel <= 0) {
      state.tokenize = tokenBase;
    }
    return 'comment';
  }

  return {
    startState: function() {return {tokenize: tokenBase, commentLevel:
0};},
    token: function(stream, state) {
      if (stream.eatSpace()) return null;
      return state.tokenize(stream, state);
    },
    blockCommentStart: "(*",
    blockCommentEnd: "*)"
  };
});

CodeMirror.defineMIME('text/x-mathematica', {
  name: 'mathematica'
});

});