1// CodeMirror, copyright (c) by Marijn Haverbeke and others 2// Distributed under an MIT license: http://codemirror.net/LICENSE 3 4 5(function(mod) { 6 if (typeof exports == "object" && typeof module == "object") // CommonJS 7 mod(require("../../lib/codemirror")); 8 else if (typeof define == "function" && define.amd) // AMD 9 define(["../../lib/codemirror"], mod); 10 else // Plain browser env 11 mod(CodeMirror); 12})(function(CodeMirror) { 13"use strict"; 14 15 CodeMirror.defineMode("svx", function(config) { 16 var indentUnit = config.indentUnit; 17 18 var keywords = { 19 "\\TLV":"keyword", "\\SV":"keyword", "m4":"def", "M4":"def", "\\TLV_version":"keyword" 20 }; 21 22 var kpScopePrefixs = { 23 "**":"variable-2", "*":"variable-2", "$$":"variable", "$":"variable", 24 "^^":"attribute", "^":"attribute" 25 }; 26 27 var chScopePrefixs = { 28 ">":"property", "->":"property", "-":"hr", "|":"link", "?$":"qualifier", "?*":"qualifier", 29 "@-":"variable-3", "@":"variable-3", "?":"qualifier" 30 }; 31 32 var unsignedNumber = /\d[0-9_]*/; 33 var decimalLiteral = /\d*\s*'s?d\s*\d[0-9_]*/i; 34 var binaryLiteral = /\d*\s*'s?b\s*[xz01][xz01_]*/i; 35 var octLiteral = /\d*\s*'s?o\s*[xz0-7][xz0-7_]*/i; 36 var hexLiteral = /\d*\s*'s?h\s*[0-9a-fxz?][0-9a-fxz?_]*/i; 37 var realLiteral = /(\d[\d_]*(\.\d[\d_]*)?E-?[\d_]+)|(\d[\d_]*\.\d[\d_]*)/i; 38 39 var isOperatorChar = /[\[\]=:]/; 40 var curPunc; 41 var curScope; 42 43 function tokenBase(stream, state) { 44 var ctx = state.context; 45 if (state.startOfLine) {curScope=""; state.startOfLine=false;}; 46 var ch = stream.next(); 47 // strings 48 if (ch == '"') { 49 state.tokenize = tokenString(ch); 50 return state.tokenize(stream, state); 51 } 52 // \SV region change keywords 53 if ((stream.pos == 1) && (/\\SV/.test(stream.string))) { 54 curScope = "ch"; 55 curPunc = stream.string; 56 if (/\\TLV_version/.test(stream.string)) {curPunc = "\\TLV_version";}; 57 stream.skipToEnd(); 58 if (curPunc=="\\SV") { 59 state.tokenize = tokenSvRegion; 60 return keywords[curPunc]; 61 }; 62 if (keywords.propertyIsEnumerable(curPunc)) { return keywords[curPunc];}; 63 return "builtin"; 64 } 65 // bypass nesting and 1 char punc 66 if (/[\[\]{}\(\);\:]/.test(ch)) { 67 curPunc = ch; 68 return "meta"; 69 } 70 // Numeric literals + m4 macro + @ stages 71 if (stream.match(realLiteral) || 72 stream.match(decimalLiteral) || 73 stream.match(binaryLiteral) || 74 stream.match(octLiteral) || 75 stream.match(hexLiteral) || 76 stream.match(unsignedNumber) || 77 stream.match(realLiteral)) { 78 curPunc = stream.current(); 79 var style = (/@/.test(curPunc.charAt(0))) ? chScopePrefixs[curPunc.charAt(0)] 80 : ( ((/\b[mM]4+?/.test(curPunc))) ? keywords[curPunc] : "number"); 81 curScope = (curScope=="" && (style!="number")) ? "ch" : "kp"; 82 if (style=="def") stream.skipTo("("); 83 return style; 84 } 85 // comments 86 if (ch == "/") { 87 if (stream.eat("*")) { 88 state.tokenize = tokenComment; 89 return tokenComment(stream, state); 90 } 91 if (stream.eat("/")) { 92 stream.skipToEnd(); 93 return "comment"; 94 } 95 } 96 // sv hints? 97 if ((ch == "!") && stream.pos==1) { 98 stream.eat("!"); 99 return "comment"; 100 } 101 // operators 102 if (isOperatorChar.test(ch)) { 103 stream.eatWhile(isOperatorChar); 104 return "operator"; 105 } 106 // phy hier 107 if ((curScope != "") && (ch == "#")) { 108 stream.eatWhile(/#[+-]\d/); 109 curPunc = stream.current(); 110 curScope="ch"; 111 return "tag"; 112 } 113 // needed? Ask Steve 114 if ((/\.\.\.;/.test(stream.string))) { //bozo needed? Ask Steve 115 curScope = "kp"; 116 curPunc = stream.string; 117 return "builtin"; 118 }; 119 // special SVX operators 120 stream.match(/[a-zA-Z_0-9]+/); 121 curPunc = stream.current(); 122 var firstCh = curPunc.charAt(0); 123 var style; 124 125 if (kpScopePrefixs.propertyIsEnumerable(firstCh)) { 126 curScope = (curScope=="") ?"kp":curScope; 127 style = kpScopePrefixs[firstCh]; 128 return style; 129 } 130 if (chScopePrefixs.propertyIsEnumerable(firstCh)) { 131 curScope = (curScope=="") ?"ch":curScope; 132 style = chScopePrefixs[firstCh]; 133 return style; 134 } 135 if (stream.match(/^[A-Z0-9]+/)) {curScope="kp";return "def";}; 136 return "builtin"; 137 } 138 function tokenString(quote) { 139 return function(stream, state) { 140 var escaped = false, next, end = false;
141 while ((next = stream.next()) != null) { 142 if (next == quote && !escaped) {end = true; break;} 143 escaped = !escaped && next == "\\"; 144 } 145 if (end || !(escaped || quote == "`")) 146 state.tokenize = tokenBase; 147 return "string"; 148 }; 149 } 150 function tokenComment(stream, state) { 151 var maybeEnd = false, ch; 152 while (ch = stream.next()) { 153 if (ch == "/" && maybeEnd) { 154 state.tokenize = null; 155 break; 156 } 157 maybeEnd = (ch == "*"); 158 } 159 return "comment"; 160 } 161 function tokenSvRegionComment(stream, state) { 162 var maybeEnd = false, ch; 163 while (ch = stream.next()) { 164 if (ch == "/" && maybeEnd) { 165 state.tokenize = tokenSvRegion; 166 break; 167 } 168 maybeEnd = (ch == "*"); 169 } 170 return "comment"; 171 } 172 function tokenSvRegion(stream, state) { 173 var ch; 174 while ( ch=stream.next() ) { 175 if (ch == "\\" && stream.pos==1 && /[\\TLV]/.test(stream.string) ) { 176 stream.backUp(1); 177 state.tokenize = null; 178 break; 179 } 180 if ((ch == "/") && stream.eat("*")) { 181 state.tokenize = tokenSvRegionComment; 182 return tokenSvRegionComment(stream, state); 183 } 184 } 185 return "atom"; 186 } 187 function Context(indented, column, align, prev, punc) { 188 this.indented = indented; 189 this.column = column; 190 this.align = align; 191 this.prev = prev; 192 this.punc = punc; 193 this.doIndent = false; 194 } 195 function pushContext(state, punc) { 196 return state.context = new Context(state.indented, state.column, false, state.context, punc); 197 } 198 function popContext(state) { 199 var t = state.context.punc; 200 state.indented = state.context.indented; 201 return state.context = state.context.prev; 202 } 203 function pop2CtxLvlsReIndent(state) { 204 state.context = state.context.prev; 205 state.context = state.context.prev; 206 state.indented = state.context.indented; 207 return state.context ; 208 } 209 function pop2TopCtxLvlReIndent(state) { 210 var column = state.context.column; 211 while ( column != 0) { 212 state.context = state.context.prev; 213 column = state.context.column; 214 }; 215 state.column = state.context.column; 216 return state.context ; 217 } 218 219 // Interface 220 221 return { 222 startState: function(basecolumn) { 223 return { 224 tokenize: null, 225 context: new Context((basecolumn || 0) - indentUnit, 0, "top", null,""), 226 indented: 0, 227 startOfLine: true 228 }; 229 }, 230 231 token: function(stream, state) { 232 var ctx = state.context; 233 if (stream.sol()) { 234 if (ctx.align == null) ctx.align = false; 235 state.indented = stream.indentation(); 236 state.startOfLine = true; 237 } 238 if (stream.eatSpace()) return null; 239 curPunc = null; 240 var doIndent = false; 241 var style = (state.tokenize || tokenBase)(stream, state); 242 if (style == "comment") return style; 243 if (style == "atom") return style; 244 if (ctx.align == null) ctx.align = true; 245 246 if (curScope == "ch") { 247 if (curPunc==null) { // bozo 248 curPunc="~"; 249 }; 250 var curPuncFirstChar = curPunc.charAt(0); 251 var prevPuncFirstChar = ctx.punc.charAt(0); 252 if (curPuncFirstChar != prevPuncFirstChar) { 253 if (curPuncFirstChar == "\\") {pop2TopCtxLvlReIndent(state);} 254 else if ((/[mM]/.test(curPuncFirstChar)) && prevPuncFirstChar=="@") {pop2CtxLvlsReIndent(state);} 255 else if ( /[mM]/.test(curPuncFirstChar)) {pushContext(state, curPunc); doIndent=true;} 256 else if ( /[>-\?#]/.test(curPuncFirstChar)) {pushContext(state, curPunc); doIndent=true;} 257 else if (curPuncFirstChar=="@" && prevPuncFirstChar=="|") {pushContext(state, curPunc); doIndent=true;} 258 else if (curPuncFirstChar=="@") {pushContext(state, curPunc); doIndent=true;} 259 else if (curPuncFirstChar=="|" && prevPuncFirstChar=="@") {pop2CtxLvlsReIndent(state);} 260 else if (curPuncFirstChar=="|") {pushContext(state, curPunc); doIndent=true;} 261 else {pushContext(state, curPunc); doIndent=true;}; 262 } else { 263 if (curPuncFirstChar=="@") { 264 ctx.indented = state.column - ctx.column; 265 state.column = ctx.column; 266 }; 267 } 268 } else { 269 state.column = state.column + ctx.indented; 270 ctx.indented = 0; 271 }; 272 //state.startOfLine = false;
273 ctx.doIndent = doIndent; 274 return style; 275 }, 276 277 indent: function(state, textAfter) { 278 if (state.tokenize != tokenBase && state.tokenize != null) return 0; 279 var ctx = state.context, firstChar = textAfter && textAfter.charAt(0); 280 if (ctx.indented != 0) { 281 var i = ctx.indented + ctx.column; 282 state.context.indented = 0; 283 return i; 284 } 285 if (ctx.doIndent) { 286 ctx.doIndent = false; 287 return (ctx.column+indentUnit); 288 } 289 return ctx.column ; 290 }, 291 292 electricChars: "@|", 293 fold: "brace", 294 blockCommentStart: "/*", 295 blockCommentEnd: "*/", 296 lineComment: "//" 297 }; 298 }); 299 300 CodeMirror.defineMIME("text/x-svx", "svx"); 301 302}); 303 304
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.