UNPKG

9.46 kBJavaScriptView Raw
1'use strict';
2
3Object.defineProperty(exports, '__esModule', { value: true });
4
5var prism = require('../prism/index.cjs.js');
6var theme = require('../themes/duotoneDark');
7var react = require('react');
8
9function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; }
10
11var theme__default = /*#__PURE__*/_interopDefaultLegacy(theme);
12
13var defaultProps = {
14 // $FlowFixMe
15 Prism: prism,
16 theme: theme__default['default']
17};
18
19function _defineProperty(obj, key, value) {
20 if (key in obj) {
21 Object.defineProperty(obj, key, {
22 value: value,
23 enumerable: true,
24 configurable: true,
25 writable: true
26 });
27 } else {
28 obj[key] = value;
29 }
30
31 return obj;
32}
33
34function _extends() {
35 _extends = Object.assign || function (target) {
36 for (var i = 1; i < arguments.length; i++) {
37 var source = arguments[i];
38
39 for (var key in source) {
40 if (Object.prototype.hasOwnProperty.call(source, key)) {
41 target[key] = source[key];
42 }
43 }
44 }
45
46 return target;
47 };
48
49 return _extends.apply(this, arguments);
50}
51
52var newlineRe = /\r\n|\r|\n/; // Empty lines need to contain a single empty token, denoted with { empty: true }
53
54var normalizeEmptyLines = function (line) {
55 if (line.length === 0) {
56 line.push({
57 types: ["plain"],
58 content: "\n",
59 empty: true
60 });
61 } else if (line.length === 1 && line[0].content === "") {
62 line[0].content = "\n";
63 line[0].empty = true;
64 }
65};
66
67var appendTypes = function (types, add) {
68 var typesSize = types.length;
69
70 if (typesSize > 0 && types[typesSize - 1] === add) {
71 return types;
72 }
73
74 return types.concat(add);
75}; // Takes an array of Prism's tokens and groups them by line, turning plain
76// strings into tokens as well. Tokens can become recursive in some cases,
77// which means that their types are concatenated. Plain-string tokens however
78// are always of type "plain".
79// This is not recursive to avoid exceeding the call-stack limit, since it's unclear
80// how nested Prism's tokens can become
81
82
83var normalizeTokens = function (tokens) {
84 var typeArrStack = [[]];
85 var tokenArrStack = [tokens];
86 var tokenArrIndexStack = [0];
87 var tokenArrSizeStack = [tokens.length];
88 var i = 0;
89 var stackIndex = 0;
90 var currentLine = [];
91 var acc = [currentLine];
92
93 while (stackIndex > -1) {
94 while ((i = tokenArrIndexStack[stackIndex]++) < tokenArrSizeStack[stackIndex]) {
95 var content = void 0;
96 var types = typeArrStack[stackIndex];
97 var tokenArr = tokenArrStack[stackIndex];
98 var token = tokenArr[i]; // Determine content and append type to types if necessary
99
100 if (typeof token === "string") {
101 types = stackIndex > 0 ? types : ["plain"];
102 content = token;
103 } else {
104 types = appendTypes(types, token.type);
105
106 if (token.alias) {
107 types = appendTypes(types, token.alias);
108 }
109
110 content = token.content;
111 } // If token.content is an array, increase the stack depth and repeat this while-loop
112
113
114 if (typeof content !== "string") {
115 stackIndex++;
116 typeArrStack.push(types);
117 tokenArrStack.push(content);
118 tokenArrIndexStack.push(0);
119 tokenArrSizeStack.push(content.length);
120 continue;
121 } // Split by newlines
122
123
124 var splitByNewlines = content.split(newlineRe);
125 var newlineCount = splitByNewlines.length;
126 currentLine.push({
127 types: types,
128 content: splitByNewlines[0]
129 }); // Create a new line for each string on a new line
130
131 for (var i$1 = 1; i$1 < newlineCount; i$1++) {
132 normalizeEmptyLines(currentLine);
133 acc.push(currentLine = []);
134 currentLine.push({
135 types: types,
136 content: splitByNewlines[i$1]
137 });
138 }
139 } // Decreate the stack depth
140
141
142 stackIndex--;
143 typeArrStack.pop();
144 tokenArrStack.pop();
145 tokenArrIndexStack.pop();
146 tokenArrSizeStack.pop();
147 }
148
149 normalizeEmptyLines(currentLine);
150 return acc;
151};
152
153var themeToDict = function (theme, language) {
154 var plain = theme.plain; // $FlowFixMe
155
156 var base = Object.create(null);
157 var themeDict = theme.styles.reduce(function (acc, themeEntry) {
158 var languages = themeEntry.languages;
159 var style = themeEntry.style;
160
161 if (languages && !languages.includes(language)) {
162 return acc;
163 }
164
165 themeEntry.types.forEach(function (type) {
166 // $FlowFixMe
167 var accStyle = _extends({}, acc[type], style);
168
169 acc[type] = accStyle;
170 });
171 return acc;
172 }, base); // $FlowFixMe
173
174 themeDict.root = plain; // $FlowFixMe
175
176 themeDict.plain = _extends({}, plain, {
177 backgroundColor: null
178 });
179 return themeDict;
180};
181
182function objectWithoutProperties(obj, exclude) {
183 var target = {};
184
185 for (var k in obj) if (Object.prototype.hasOwnProperty.call(obj, k) && exclude.indexOf(k) === -1) target[k] = obj[k];
186
187 return target;
188}
189
190var Highlight = /*@__PURE__*/function (Component) {
191 function Highlight() {
192 var this$1 = this;
193 var args = [],
194 len = arguments.length;
195
196 while (len--) args[len] = arguments[len];
197
198 Component.apply(this, args);
199
200 _defineProperty(this, "getThemeDict", function (props) {
201 if (this$1.themeDict !== undefined && props.theme === this$1.prevTheme && props.language === this$1.prevLanguage) {
202 return this$1.themeDict;
203 }
204
205 this$1.prevTheme = props.theme;
206 this$1.prevLanguage = props.language;
207 var themeDict = props.theme ? themeToDict(props.theme, props.language) : undefined;
208 return this$1.themeDict = themeDict;
209 });
210
211 _defineProperty(this, "getLineProps", function (ref) {
212 var key = ref.key;
213 var className = ref.className;
214 var style = ref.style;
215 var rest$1 = objectWithoutProperties(ref, ["key", "className", "style", "line"]);
216 var rest = rest$1;
217
218 var output = _extends({}, rest, {
219 className: "token-line",
220 style: undefined,
221 key: undefined
222 });
223
224 var themeDict = this$1.getThemeDict(this$1.props);
225
226 if (themeDict !== undefined) {
227 output.style = themeDict.plain;
228 }
229
230 if (style !== undefined) {
231 output.style = output.style !== undefined ? _extends({}, output.style, style) : style;
232 }
233
234 if (key !== undefined) {
235 output.key = key;
236 }
237
238 if (className) {
239 output.className += " " + className;
240 }
241
242 return output;
243 });
244
245 _defineProperty(this, "getStyleForToken", function (ref) {
246 var types = ref.types;
247 var empty = ref.empty;
248 var typesSize = types.length;
249 var themeDict = this$1.getThemeDict(this$1.props);
250
251 if (themeDict === undefined) {
252 return undefined;
253 } else if (typesSize === 1 && types[0] === "plain") {
254 return empty ? {
255 display: "inline-block"
256 } : undefined;
257 } else if (typesSize === 1 && !empty) {
258 return themeDict[types[0]];
259 }
260
261 var baseStyle = empty ? {
262 display: "inline-block"
263 } : {}; // $FlowFixMe
264
265 var typeStyles = types.map(function (type) {
266 return themeDict[type];
267 });
268 return Object.assign.apply(Object, [baseStyle].concat(typeStyles));
269 });
270
271 _defineProperty(this, "getTokenProps", function (ref) {
272 var key = ref.key;
273 var className = ref.className;
274 var style = ref.style;
275 var token = ref.token;
276 var rest$1 = objectWithoutProperties(ref, ["key", "className", "style", "token"]);
277 var rest = rest$1;
278
279 var output = _extends({}, rest, {
280 className: "token " + token.types.join(" "),
281 children: token.content,
282 style: this$1.getStyleForToken(token),
283 key: undefined
284 });
285
286 if (style !== undefined) {
287 output.style = output.style !== undefined ? _extends({}, output.style, style) : style;
288 }
289
290 if (key !== undefined) {
291 output.key = key;
292 }
293
294 if (className) {
295 output.className += " " + className;
296 }
297
298 return output;
299 });
300
301 _defineProperty(this, "tokenize", function (Prism, code, grammar, language) {
302 var env = {
303 code: code,
304 grammar: grammar,
305 language: language,
306 tokens: []
307 };
308 Prism.hooks.run("before-tokenize", env);
309 var tokens = env.tokens = Prism.tokenize(env.code, env.grammar, env.language);
310 Prism.hooks.run("after-tokenize", env);
311 return tokens;
312 });
313 }
314
315 if (Component) Highlight.__proto__ = Component;
316 Highlight.prototype = Object.create(Component && Component.prototype);
317 Highlight.prototype.constructor = Highlight;
318
319 Highlight.prototype.render = function render() {
320 var ref = this.props;
321 var Prism = ref.Prism;
322 var language = ref.language;
323 var code = ref.code;
324 var children = ref.children;
325 var themeDict = this.getThemeDict(this.props);
326 var grammar = Prism.languages[language];
327 var mixedTokens = grammar !== undefined ? this.tokenize(Prism, code, grammar, language) : [code];
328 var tokens = normalizeTokens(mixedTokens);
329 return children({
330 tokens: tokens,
331 className: "prism-code language-" + language,
332 style: themeDict !== undefined ? themeDict.root : {},
333 getLineProps: this.getLineProps,
334 getTokenProps: this.getTokenProps
335 });
336 };
337
338 return Highlight;
339}(react.Component);
340
341exports.Prism = prism;
342exports.default = Highlight;
343exports.defaultProps = defaultProps;