summaryrefslogtreecommitdiff
path: root/microlight.js
diff options
context:
space:
mode:
Diffstat (limited to 'microlight.js')
-rw-r--r--microlight.js206
1 files changed, 206 insertions, 0 deletions
diff --git a/microlight.js b/microlight.js
new file mode 100644
index 0000000..3d56fa2
--- /dev/null
+++ b/microlight.js
@@ -0,0 +1,206 @@
1/**
2 * @fileoverview microlight - syntax highlightning library
3 * @version 0.0.1
4 *
5 * @license MIT, see http://github.com/asvd/microlight
6 * @copyright 2015 asvd <heliosframework@gmail.com>
7 *
8 * Code structure aims at minimizing the compressed library size
9 */
10
11
12(function (root, factory) {
13 if (typeof define === 'function' && define.amd) {
14 define(['exports'], factory);
15 } else if (typeof exports !== 'undefined') {
16 factory(exports);
17 } else {
18 factory((root.microlight = {}));
19 }
20}(this, function (exports) {
21 // for better compression
22 var _window = window,
23 _document = document,
24 appendChild = 'appendChild',
25 test = 'test',
26 // style and color templates
27 textShadow = ';text-shadow:',
28 opacity = 'opacity:.',
29 _0px_0px = ' 0px 0px ',
30 _3px_0px_5 = '3px 0px 5',
31 brace = ')',
32
33 el, // current microlighted element to run through
34
35 // dynamic set of nodes to highlight
36 microlighted = _document.getElementsByClassName('microlight');
37
38
39 var reset = function(i) {
40 for (i = 0; el = microlighted[i++];) {
41 var text = el.textContent,
42 pos = 0, // current position
43 next1 = text[0], // next character
44 chr = 1, // current character
45 prev1, // previous character
46 prev2, // the one before the previous
47 token = // current token content
48 el.innerHTML = '', // (and cleaning the node)
49
50 // current token type:
51 // 0: anything else (whitespaces / newlines)
52 // 1: operator or brace
53 // 2: closing braces (after which '/' is division not regex)
54 // 3: (key)word
55 // 4: regex
56 // 5: string starting with "
57 // 6: string starting with '
58 // 7: xml comment <!-- -->
59 // 8: multiline comment /* */
60 // 9: single-line comment starting with two slashes //
61 // 10: single-line comment starting with hash #
62 tokenType = 0,
63
64 // kept to determine between regex and division
65 lastTokenType,
66 // flag determining if token is multi-character
67 multichar,
68 node,
69
70 // calculating the colors for the style templates
71 colorArr = /(\d*\, \d*\, \d*)(, ([.\d]*))?/g.exec(
72 _window.getComputedStyle(el).color
73 ),
74 pxColor = 'px rgba('+colorArr[1]+',',
75 alpha = colorArr[3]||1;
76
77 // running through characters and highlighting
78 while (prev2 = prev1,
79 // escaping if needed (with except for comments)
80 // pervious character will not be therefore
81 // recognized as a token finalize condition
82 prev1 = tokenType < 7 && prev1 == '\\' ? 1 : chr
83 ) {
84 chr = next1;
85 next1=text[++pos];
86 multichar = token.length > 1;
87
88 // checking if current token should be finalized
89 if (!chr || // end of content
90 // types 9-10 (single-line comments) end with a
91 // newline
92 (tokenType > 8 && chr == '\n') ||
93 [ // finalize conditions for other token types
94 // 0: whitespaces
95 /\S/[test](chr), // merged together
96 // 1: operators
97 1, // consist of a single character
98 // 2: braces
99 1, // consist of a single character
100 // 3: (key)word
101 !/[$\w]/[test](chr),
102 // 4: regex
103 (prev1 == '/' || prev1 == '\n') && multichar,
104 // 5: string with "
105 prev1 == '"' && multichar,
106 // 6: string with '
107 prev1 == "'" && multichar,
108 // 7: xml comment
109 text[pos-4]+prev2+prev1 == '-->',
110 // 8: multiline comment
111 prev2+prev1 == '*/'
112 ][tokenType]
113 ) {
114 // appending the token to the result
115 if (token) {
116 // remapping token type into style
117 // (some types are highlighted similarly)
118 el[appendChild](
119 node = _document.createElement('span')
120 ).setAttribute('style', [
121 // 0: not formatted
122 '',
123 // 1: punctuation
124 opacity + 6 +
125 textShadow + _0px_0px+7+pxColor + alpha / 4 + '),' +
126 _0px_0px+3+pxColor + alpha / 4 + brace,
127 // 2: keywords
128 textShadow + _0px_0px+9+pxColor + alpha * .7 + '),' +
129 _0px_0px+2+pxColor + alpha * .4 + brace,
130 // 3: strings and regexps
131 opacity + 7 +
132 textShadow + _3px_0px_5+pxColor + alpha / 5 + '),-' +
133 _3px_0px_5+pxColor + alpha / 5 + brace,
134 // 4: comments
135 'font-style:italic;'+
136 opacity + 5 +
137 textShadow + _3px_0px_5+pxColor + alpha / 4 + '),-' +
138 _3px_0px_5+pxColor + alpha / 4 + brace
139 ][
140 // not formatted
141 !tokenType ? 0 :
142 // punctuation
143 tokenType < 3 ? 1 :
144 // comments
145 tokenType > 6 ? 4 :
146 // regex and strings
147 tokenType > 3 ? 3 :
148 // otherwise tokenType == 3, (key)word
149 // (2 if regexp matches, 0 otherwise)
150 2 * /^(a(bstract|lias|nd|rguments|rray|s(m|sert)?|uto)|b(ase|egin|ool(ean)?|reak|yte)|c(ase|atch|har|hecked|lass|lone|ompl|onst|ontinue)|de(bugger|cimal|clare|f(ault|er)?|init|l(egate|ete)?)|do|double|e(cho|ls?if|lse(if)?|nd|nsure|num|vent|x(cept|ec|p(licit|ort)|te(nds|nsion|rn)))|f(allthrough|alse|inal(ly)?|ixed|loat|or(each)?|riend|rom|unc(tion)?)|global|goto|guard|i(f|mp(lements|licit|ort)|n(it|clude(_once)?|line|out|stanceof|t(erface|ernal)?)?|s)|l(ambda|et|ock|ong)|m(icrolight|odule|utable)|NaN|n(amespace|ative|ext|ew|il|ot|ull)|o(bject|perator|r|ut|verride)|p(ackage|arams|rivate|rotected|rotocol|ublic)|r(aise|e(adonly|do|f|gister|peat|quire(_once)?|scue|strict|try|turn))|s(byte|ealed|elf|hort|igned|izeof|tatic|tring|truct|ubscript|uper|ynchronized|witch)|t(emplate|hen|his|hrows?|ransient|rue|ry|ype(alias|def|id|name|of))|u(n(checked|def(ined)?|ion|less|signed|til)|se|sing)|v(ar|irtual|oid|olatile)|w(char_t|hen|here|hile|ith)|xor|yield)$/[test](token)
151 ]);
152
153 node[appendChild](_document.createTextNode(token));
154 }
155
156 // saving the previous token type
157 // (skipping whitespaces and comments)
158 lastTokenType =
159 (tokenType && tokenType < 7) ?
160 tokenType : lastTokenType;
161
162 // initializing a new token
163 token = '';
164
165 // determining the new token type (going down
166 // until matching a token type start condition)
167 tokenType = 11;
168 while (![
169 1, // 0: whitespace
170 // 1: operator or braces
171 /[\/{}[(\-+*=<>:;|\\.,?!&@~]/[test](chr),
172 /[\])]/[test](chr), // 2: closing brace
173 /[$\w]/[test](chr), // 3: (key)word
174 chr == '/' && // 4: regex
175 // previous token was an
176 // opening brace or an
177 // operator (otherwise
178 // division, not a regex)
179 (lastTokenType < 2) &&
180 // workaround for xml
181 // closing tags
182 prev1 != '<',
183 chr == '"', // 5: string with "
184 chr == "'", // 6: string with '
185 // 7: xml comment
186 chr+next1+text[pos+1]+text[pos+2] == '<!--',
187 chr+next1 == '/*', // 8: multiline comment
188 chr+next1 == '//', // 9: single-line comment
189 chr == '#' // 10: hash-style comment
190 ][--tokenType]);
191 }
192
193 token += chr;
194 }
195 }
196 }
197
198 exports.reset = reset;
199
200 if (_document.readyState == 'complete') {
201 reset();
202 } else {
203 _window.addEventListener('load', reset, 0);
204 }
205}));
206