github.com/elliott5/community@v0.14.1-0.20160709191136-823126fb026a/app/public/codemirror/mode/modelica/modelica.js (about)

     1  // CodeMirror, copyright (c) by Marijn Haverbeke and others
     2  // Distributed under an MIT license: http://codemirror.net/LICENSE
     3  
     4  // Modelica support for CodeMirror, copyright (c) by Lennart Ochel
     5  
     6  (function(mod) {
     7    if (typeof exports == "object" && typeof module == "object") // CommonJS
     8      mod(require("../../lib/codemirror"));
     9    else if (typeof define == "function" && define.amd) // AMD
    10      define(["../../lib/codemirror"], mod);
    11    else // Plain browser env
    12      mod(CodeMirror);
    13  })
    14  
    15  (function(CodeMirror) {
    16    "use strict";
    17  
    18    CodeMirror.defineMode("modelica", function(config, parserConfig) {
    19  
    20      var indentUnit = config.indentUnit;
    21      var keywords = parserConfig.keywords || {};
    22      var builtin = parserConfig.builtin || {};
    23      var atoms = parserConfig.atoms || {};
    24  
    25      var isSingleOperatorChar = /[;=\(:\),{}.*<>+\-\/^\[\]]/;
    26      var isDoubleOperatorChar = /(:=|<=|>=|==|<>|\.\+|\.\-|\.\*|\.\/|\.\^)/;
    27      var isDigit = /[0-9]/;
    28      var isNonDigit = /[_a-zA-Z]/;
    29  
    30      function tokenLineComment(stream, state) {
    31        stream.skipToEnd();
    32        state.tokenize = null;
    33        return "comment";
    34      }
    35  
    36      function tokenBlockComment(stream, state) {
    37        var maybeEnd = false, ch;
    38        while (ch = stream.next()) {
    39          if (maybeEnd && ch == "/") {
    40            state.tokenize = null;
    41            break;
    42          }
    43          maybeEnd = (ch == "*");
    44        }
    45        return "comment";
    46      }
    47  
    48      function tokenString(stream, state) {
    49        var escaped = false, ch;
    50        while ((ch = stream.next()) != null) {
    51          if (ch == '"' && !escaped) {
    52            state.tokenize = null;
    53            state.sol = false;
    54            break;
    55          }
    56          escaped = !escaped && ch == "\\";
    57        }
    58  
    59        return "string";
    60      }
    61  
    62      function tokenIdent(stream, state) {
    63        stream.eatWhile(isDigit);
    64        while (stream.eat(isDigit) || stream.eat(isNonDigit)) { }
    65  
    66  
    67        var cur = stream.current();
    68  
    69        if(state.sol && (cur == "package" || cur == "model" || cur == "when" || cur == "connector")) state.level++;
    70        else if(state.sol && cur == "end" && state.level > 0) state.level--;
    71  
    72        state.tokenize = null;
    73        state.sol = false;
    74  
    75        if (keywords.propertyIsEnumerable(cur)) return "keyword";
    76        else if (builtin.propertyIsEnumerable(cur)) return "builtin";
    77        else if (atoms.propertyIsEnumerable(cur)) return "atom";
    78        else return "variable";
    79      }
    80  
    81      function tokenQIdent(stream, state) {
    82        while (stream.eat(/[^']/)) { }
    83  
    84        state.tokenize = null;
    85        state.sol = false;
    86  
    87        if(stream.eat("'"))
    88          return "variable";
    89        else
    90          return "error";
    91      }
    92  
    93      function tokenUnsignedNuber(stream, state) {
    94        stream.eatWhile(isDigit);
    95        if (stream.eat('.')) {
    96          stream.eatWhile(isDigit);
    97        }
    98        if (stream.eat('e') || stream.eat('E')) {
    99          if (!stream.eat('-'))
   100            stream.eat('+');
   101          stream.eatWhile(isDigit);
   102        }
   103  
   104        state.tokenize = null;
   105        state.sol = false;
   106        return "number";
   107      }
   108  
   109      // Interface
   110      return {
   111        startState: function() {
   112          return {
   113            tokenize: null,
   114            level: 0,
   115            sol: true
   116          };
   117        },
   118  
   119        token: function(stream, state) {
   120          if(state.tokenize != null) {
   121            return state.tokenize(stream, state);
   122          }
   123  
   124          if(stream.sol()) {
   125            state.sol = true;
   126          }
   127  
   128          // WHITESPACE
   129          if(stream.eatSpace()) {
   130            state.tokenize = null;
   131            return null;
   132          }
   133  
   134          var ch = stream.next();
   135  
   136          // LINECOMMENT
   137          if(ch == '/' && stream.eat('/')) {
   138            state.tokenize = tokenLineComment;
   139          }
   140          // BLOCKCOMMENT
   141          else if(ch == '/' && stream.eat('*')) {
   142            state.tokenize = tokenBlockComment;
   143          }
   144          // TWO SYMBOL TOKENS
   145          else if(isDoubleOperatorChar.test(ch+stream.peek())) {
   146            stream.next();
   147            state.tokenize = null;
   148            return "operator";
   149          }
   150          // SINGLE SYMBOL TOKENS
   151          else if(isSingleOperatorChar.test(ch)) {
   152            state.tokenize = null;
   153            return "operator";
   154          }
   155          // IDENT
   156          else if(isNonDigit.test(ch)) {
   157            state.tokenize = tokenIdent;
   158          }
   159          // Q-IDENT
   160          else if(ch == "'" && stream.peek() && stream.peek() != "'") {
   161            state.tokenize = tokenQIdent;
   162          }
   163          // STRING
   164          else if(ch == '"') {
   165            state.tokenize = tokenString;
   166          }
   167          // UNSIGNED_NUBER
   168          else if(isDigit.test(ch)) {
   169            state.tokenize = tokenUnsignedNuber;
   170          }
   171          // ERROR
   172          else {
   173            state.tokenize = null;
   174            return "error";
   175          }
   176  
   177          return state.tokenize(stream, state);
   178        },
   179  
   180        indent: function(state, textAfter) {
   181          if (state.tokenize != null) return CodeMirror.Pass;
   182  
   183          var level = state.level;
   184          if(/(algorithm)/.test(textAfter)) level--;
   185          if(/(equation)/.test(textAfter)) level--;
   186          if(/(initial algorithm)/.test(textAfter)) level--;
   187          if(/(initial equation)/.test(textAfter)) level--;
   188          if(/(end)/.test(textAfter)) level--;
   189  
   190          if(level > 0)
   191            return indentUnit*level;
   192          else
   193            return 0;
   194        },
   195  
   196        blockCommentStart: "/*",
   197        blockCommentEnd: "*/",
   198        lineComment: "//"
   199      };
   200    });
   201  
   202    function words(str) {
   203      var obj = {}, words = str.split(" ");
   204      for (var i=0; i<words.length; ++i)
   205        obj[words[i]] = true;
   206      return obj;
   207    }
   208  
   209    var modelicaKeywords = "algorithm and annotation assert block break class connect connector constant constrainedby der discrete each else elseif elsewhen encapsulated end enumeration equation expandable extends external false final flow for function if import impure in initial inner input loop model not operator or outer output package parameter partial protected public pure record redeclare replaceable return stream then true type when while within";
   210    var modelicaBuiltin = "abs acos actualStream asin atan atan2 cardinality ceil cos cosh delay div edge exp floor getInstanceName homotopy inStream integer log log10 mod pre reinit rem semiLinear sign sin sinh spatialDistribution sqrt tan tanh";
   211    var modelicaAtoms = "Real Boolean Integer String";
   212  
   213    function def(mimes, mode) {
   214      if (typeof mimes == "string")
   215        mimes = [mimes];
   216  
   217      var words = [];
   218  
   219      function add(obj) {
   220        if (obj)
   221          for (var prop in obj)
   222            if (obj.hasOwnProperty(prop))
   223              words.push(prop);
   224      }
   225  
   226      add(mode.keywords);
   227      add(mode.builtin);
   228      add(mode.atoms);
   229  
   230      if (words.length) {
   231        mode.helperType = mimes[0];
   232        CodeMirror.registerHelper("hintWords", mimes[0], words);
   233      }
   234  
   235      for (var i=0; i<mimes.length; ++i)
   236        CodeMirror.defineMIME(mimes[i], mode);
   237    }
   238  
   239    def(["text/x-modelica"], {
   240      name: "modelica",
   241      keywords: words(modelicaKeywords),
   242      builtin: words(modelicaBuiltin),
   243      atoms: words(modelicaAtoms)
   244    });
   245  });