mirror of
https://github.com/neocities/neocities.git
synced 2025-05-13 07:57:16 +02:00
start on the coding assistant
This commit is contained in:
parent
8f6a85d81d
commit
8ba6005c67
546 changed files with 54575 additions and 12 deletions
774
public/js/highlight/es/languages/javascript.js
Normal file
774
public/js/highlight/es/languages/javascript.js
Normal file
|
@ -0,0 +1,774 @@
|
|||
/*! `javascript` grammar compiled for Highlight.js 11.9.0 */
|
||||
var hljsGrammar = (function () {
|
||||
'use strict';
|
||||
|
||||
const IDENT_RE = '[A-Za-z$_][0-9A-Za-z$_]*';
|
||||
const KEYWORDS = [
|
||||
"as", // for exports
|
||||
"in",
|
||||
"of",
|
||||
"if",
|
||||
"for",
|
||||
"while",
|
||||
"finally",
|
||||
"var",
|
||||
"new",
|
||||
"function",
|
||||
"do",
|
||||
"return",
|
||||
"void",
|
||||
"else",
|
||||
"break",
|
||||
"catch",
|
||||
"instanceof",
|
||||
"with",
|
||||
"throw",
|
||||
"case",
|
||||
"default",
|
||||
"try",
|
||||
"switch",
|
||||
"continue",
|
||||
"typeof",
|
||||
"delete",
|
||||
"let",
|
||||
"yield",
|
||||
"const",
|
||||
"class",
|
||||
// JS handles these with a special rule
|
||||
// "get",
|
||||
// "set",
|
||||
"debugger",
|
||||
"async",
|
||||
"await",
|
||||
"static",
|
||||
"import",
|
||||
"from",
|
||||
"export",
|
||||
"extends"
|
||||
];
|
||||
const LITERALS = [
|
||||
"true",
|
||||
"false",
|
||||
"null",
|
||||
"undefined",
|
||||
"NaN",
|
||||
"Infinity"
|
||||
];
|
||||
|
||||
// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects
|
||||
const TYPES = [
|
||||
// Fundamental objects
|
||||
"Object",
|
||||
"Function",
|
||||
"Boolean",
|
||||
"Symbol",
|
||||
// numbers and dates
|
||||
"Math",
|
||||
"Date",
|
||||
"Number",
|
||||
"BigInt",
|
||||
// text
|
||||
"String",
|
||||
"RegExp",
|
||||
// Indexed collections
|
||||
"Array",
|
||||
"Float32Array",
|
||||
"Float64Array",
|
||||
"Int8Array",
|
||||
"Uint8Array",
|
||||
"Uint8ClampedArray",
|
||||
"Int16Array",
|
||||
"Int32Array",
|
||||
"Uint16Array",
|
||||
"Uint32Array",
|
||||
"BigInt64Array",
|
||||
"BigUint64Array",
|
||||
// Keyed collections
|
||||
"Set",
|
||||
"Map",
|
||||
"WeakSet",
|
||||
"WeakMap",
|
||||
// Structured data
|
||||
"ArrayBuffer",
|
||||
"SharedArrayBuffer",
|
||||
"Atomics",
|
||||
"DataView",
|
||||
"JSON",
|
||||
// Control abstraction objects
|
||||
"Promise",
|
||||
"Generator",
|
||||
"GeneratorFunction",
|
||||
"AsyncFunction",
|
||||
// Reflection
|
||||
"Reflect",
|
||||
"Proxy",
|
||||
// Internationalization
|
||||
"Intl",
|
||||
// WebAssembly
|
||||
"WebAssembly"
|
||||
];
|
||||
|
||||
const ERROR_TYPES = [
|
||||
"Error",
|
||||
"EvalError",
|
||||
"InternalError",
|
||||
"RangeError",
|
||||
"ReferenceError",
|
||||
"SyntaxError",
|
||||
"TypeError",
|
||||
"URIError"
|
||||
];
|
||||
|
||||
const BUILT_IN_GLOBALS = [
|
||||
"setInterval",
|
||||
"setTimeout",
|
||||
"clearInterval",
|
||||
"clearTimeout",
|
||||
|
||||
"require",
|
||||
"exports",
|
||||
|
||||
"eval",
|
||||
"isFinite",
|
||||
"isNaN",
|
||||
"parseFloat",
|
||||
"parseInt",
|
||||
"decodeURI",
|
||||
"decodeURIComponent",
|
||||
"encodeURI",
|
||||
"encodeURIComponent",
|
||||
"escape",
|
||||
"unescape"
|
||||
];
|
||||
|
||||
const BUILT_IN_VARIABLES = [
|
||||
"arguments",
|
||||
"this",
|
||||
"super",
|
||||
"console",
|
||||
"window",
|
||||
"document",
|
||||
"localStorage",
|
||||
"sessionStorage",
|
||||
"module",
|
||||
"global" // Node.js
|
||||
];
|
||||
|
||||
const BUILT_INS = [].concat(
|
||||
BUILT_IN_GLOBALS,
|
||||
TYPES,
|
||||
ERROR_TYPES
|
||||
);
|
||||
|
||||
/*
|
||||
Language: JavaScript
|
||||
Description: JavaScript (JS) is a lightweight, interpreted, or just-in-time compiled programming language with first-class functions.
|
||||
Category: common, scripting, web
|
||||
Website: https://developer.mozilla.org/en-US/docs/Web/JavaScript
|
||||
*/
|
||||
|
||||
|
||||
/** @type LanguageFn */
|
||||
function javascript(hljs) {
|
||||
const regex = hljs.regex;
|
||||
/**
|
||||
* Takes a string like "<Booger" and checks to see
|
||||
* if we can find a matching "</Booger" later in the
|
||||
* content.
|
||||
* @param {RegExpMatchArray} match
|
||||
* @param {{after:number}} param1
|
||||
*/
|
||||
const hasClosingTag = (match, { after }) => {
|
||||
const tag = "</" + match[0].slice(1);
|
||||
const pos = match.input.indexOf(tag, after);
|
||||
return pos !== -1;
|
||||
};
|
||||
|
||||
const IDENT_RE$1 = IDENT_RE;
|
||||
const FRAGMENT = {
|
||||
begin: '<>',
|
||||
end: '</>'
|
||||
};
|
||||
// to avoid some special cases inside isTrulyOpeningTag
|
||||
const XML_SELF_CLOSING = /<[A-Za-z0-9\\._:-]+\s*\/>/;
|
||||
const XML_TAG = {
|
||||
begin: /<[A-Za-z0-9\\._:-]+/,
|
||||
end: /\/[A-Za-z0-9\\._:-]+>|\/>/,
|
||||
/**
|
||||
* @param {RegExpMatchArray} match
|
||||
* @param {CallbackResponse} response
|
||||
*/
|
||||
isTrulyOpeningTag: (match, response) => {
|
||||
const afterMatchIndex = match[0].length + match.index;
|
||||
const nextChar = match.input[afterMatchIndex];
|
||||
if (
|
||||
// HTML should not include another raw `<` inside a tag
|
||||
// nested type?
|
||||
// `<Array<Array<number>>`, etc.
|
||||
nextChar === "<" ||
|
||||
// the , gives away that this is not HTML
|
||||
// `<T, A extends keyof T, V>`
|
||||
nextChar === ","
|
||||
) {
|
||||
response.ignoreMatch();
|
||||
return;
|
||||
}
|
||||
|
||||
// `<something>`
|
||||
// Quite possibly a tag, lets look for a matching closing tag...
|
||||
if (nextChar === ">") {
|
||||
// if we cannot find a matching closing tag, then we
|
||||
// will ignore it
|
||||
if (!hasClosingTag(match, { after: afterMatchIndex })) {
|
||||
response.ignoreMatch();
|
||||
}
|
||||
}
|
||||
|
||||
// `<blah />` (self-closing)
|
||||
// handled by simpleSelfClosing rule
|
||||
|
||||
let m;
|
||||
const afterMatch = match.input.substring(afterMatchIndex);
|
||||
|
||||
// some more template typing stuff
|
||||
// <T = any>(key?: string) => Modify<
|
||||
if ((m = afterMatch.match(/^\s*=/))) {
|
||||
response.ignoreMatch();
|
||||
return;
|
||||
}
|
||||
|
||||
// `<From extends string>`
|
||||
// technically this could be HTML, but it smells like a type
|
||||
// NOTE: This is ugh, but added specifically for https://github.com/highlightjs/highlight.js/issues/3276
|
||||
if ((m = afterMatch.match(/^\s+extends\s+/))) {
|
||||
if (m.index === 0) {
|
||||
response.ignoreMatch();
|
||||
// eslint-disable-next-line no-useless-return
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
const KEYWORDS$1 = {
|
||||
$pattern: IDENT_RE,
|
||||
keyword: KEYWORDS,
|
||||
literal: LITERALS,
|
||||
built_in: BUILT_INS,
|
||||
"variable.language": BUILT_IN_VARIABLES
|
||||
};
|
||||
|
||||
// https://tc39.es/ecma262/#sec-literals-numeric-literals
|
||||
const decimalDigits = '[0-9](_?[0-9])*';
|
||||
const frac = `\\.(${decimalDigits})`;
|
||||
// DecimalIntegerLiteral, including Annex B NonOctalDecimalIntegerLiteral
|
||||
// https://tc39.es/ecma262/#sec-additional-syntax-numeric-literals
|
||||
const decimalInteger = `0|[1-9](_?[0-9])*|0[0-7]*[89][0-9]*`;
|
||||
const NUMBER = {
|
||||
className: 'number',
|
||||
variants: [
|
||||
// DecimalLiteral
|
||||
{ begin: `(\\b(${decimalInteger})((${frac})|\\.)?|(${frac}))` +
|
||||
`[eE][+-]?(${decimalDigits})\\b` },
|
||||
{ begin: `\\b(${decimalInteger})\\b((${frac})\\b|\\.)?|(${frac})\\b` },
|
||||
|
||||
// DecimalBigIntegerLiteral
|
||||
{ begin: `\\b(0|[1-9](_?[0-9])*)n\\b` },
|
||||
|
||||
// NonDecimalIntegerLiteral
|
||||
{ begin: "\\b0[xX][0-9a-fA-F](_?[0-9a-fA-F])*n?\\b" },
|
||||
{ begin: "\\b0[bB][0-1](_?[0-1])*n?\\b" },
|
||||
{ begin: "\\b0[oO][0-7](_?[0-7])*n?\\b" },
|
||||
|
||||
// LegacyOctalIntegerLiteral (does not include underscore separators)
|
||||
// https://tc39.es/ecma262/#sec-additional-syntax-numeric-literals
|
||||
{ begin: "\\b0[0-7]+n?\\b" },
|
||||
],
|
||||
relevance: 0
|
||||
};
|
||||
|
||||
const SUBST = {
|
||||
className: 'subst',
|
||||
begin: '\\$\\{',
|
||||
end: '\\}',
|
||||
keywords: KEYWORDS$1,
|
||||
contains: [] // defined later
|
||||
};
|
||||
const HTML_TEMPLATE = {
|
||||
begin: 'html`',
|
||||
end: '',
|
||||
starts: {
|
||||
end: '`',
|
||||
returnEnd: false,
|
||||
contains: [
|
||||
hljs.BACKSLASH_ESCAPE,
|
||||
SUBST
|
||||
],
|
||||
subLanguage: 'xml'
|
||||
}
|
||||
};
|
||||
const CSS_TEMPLATE = {
|
||||
begin: 'css`',
|
||||
end: '',
|
||||
starts: {
|
||||
end: '`',
|
||||
returnEnd: false,
|
||||
contains: [
|
||||
hljs.BACKSLASH_ESCAPE,
|
||||
SUBST
|
||||
],
|
||||
subLanguage: 'css'
|
||||
}
|
||||
};
|
||||
const GRAPHQL_TEMPLATE = {
|
||||
begin: 'gql`',
|
||||
end: '',
|
||||
starts: {
|
||||
end: '`',
|
||||
returnEnd: false,
|
||||
contains: [
|
||||
hljs.BACKSLASH_ESCAPE,
|
||||
SUBST
|
||||
],
|
||||
subLanguage: 'graphql'
|
||||
}
|
||||
};
|
||||
const TEMPLATE_STRING = {
|
||||
className: 'string',
|
||||
begin: '`',
|
||||
end: '`',
|
||||
contains: [
|
||||
hljs.BACKSLASH_ESCAPE,
|
||||
SUBST
|
||||
]
|
||||
};
|
||||
const JSDOC_COMMENT = hljs.COMMENT(
|
||||
/\/\*\*(?!\/)/,
|
||||
'\\*/',
|
||||
{
|
||||
relevance: 0,
|
||||
contains: [
|
||||
{
|
||||
begin: '(?=@[A-Za-z]+)',
|
||||
relevance: 0,
|
||||
contains: [
|
||||
{
|
||||
className: 'doctag',
|
||||
begin: '@[A-Za-z]+'
|
||||
},
|
||||
{
|
||||
className: 'type',
|
||||
begin: '\\{',
|
||||
end: '\\}',
|
||||
excludeEnd: true,
|
||||
excludeBegin: true,
|
||||
relevance: 0
|
||||
},
|
||||
{
|
||||
className: 'variable',
|
||||
begin: IDENT_RE$1 + '(?=\\s*(-)|$)',
|
||||
endsParent: true,
|
||||
relevance: 0
|
||||
},
|
||||
// eat spaces (not newlines) so we can find
|
||||
// types or variables
|
||||
{
|
||||
begin: /(?=[^\n])\s/,
|
||||
relevance: 0
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
);
|
||||
const COMMENT = {
|
||||
className: "comment",
|
||||
variants: [
|
||||
JSDOC_COMMENT,
|
||||
hljs.C_BLOCK_COMMENT_MODE,
|
||||
hljs.C_LINE_COMMENT_MODE
|
||||
]
|
||||
};
|
||||
const SUBST_INTERNALS = [
|
||||
hljs.APOS_STRING_MODE,
|
||||
hljs.QUOTE_STRING_MODE,
|
||||
HTML_TEMPLATE,
|
||||
CSS_TEMPLATE,
|
||||
GRAPHQL_TEMPLATE,
|
||||
TEMPLATE_STRING,
|
||||
// Skip numbers when they are part of a variable name
|
||||
{ match: /\$\d+/ },
|
||||
NUMBER,
|
||||
// This is intentional:
|
||||
// See https://github.com/highlightjs/highlight.js/issues/3288
|
||||
// hljs.REGEXP_MODE
|
||||
];
|
||||
SUBST.contains = SUBST_INTERNALS
|
||||
.concat({
|
||||
// we need to pair up {} inside our subst to prevent
|
||||
// it from ending too early by matching another }
|
||||
begin: /\{/,
|
||||
end: /\}/,
|
||||
keywords: KEYWORDS$1,
|
||||
contains: [
|
||||
"self"
|
||||
].concat(SUBST_INTERNALS)
|
||||
});
|
||||
const SUBST_AND_COMMENTS = [].concat(COMMENT, SUBST.contains);
|
||||
const PARAMS_CONTAINS = SUBST_AND_COMMENTS.concat([
|
||||
// eat recursive parens in sub expressions
|
||||
{
|
||||
begin: /\(/,
|
||||
end: /\)/,
|
||||
keywords: KEYWORDS$1,
|
||||
contains: ["self"].concat(SUBST_AND_COMMENTS)
|
||||
}
|
||||
]);
|
||||
const PARAMS = {
|
||||
className: 'params',
|
||||
begin: /\(/,
|
||||
end: /\)/,
|
||||
excludeBegin: true,
|
||||
excludeEnd: true,
|
||||
keywords: KEYWORDS$1,
|
||||
contains: PARAMS_CONTAINS
|
||||
};
|
||||
|
||||
// ES6 classes
|
||||
const CLASS_OR_EXTENDS = {
|
||||
variants: [
|
||||
// class Car extends vehicle
|
||||
{
|
||||
match: [
|
||||
/class/,
|
||||
/\s+/,
|
||||
IDENT_RE$1,
|
||||
/\s+/,
|
||||
/extends/,
|
||||
/\s+/,
|
||||
regex.concat(IDENT_RE$1, "(", regex.concat(/\./, IDENT_RE$1), ")*")
|
||||
],
|
||||
scope: {
|
||||
1: "keyword",
|
||||
3: "title.class",
|
||||
5: "keyword",
|
||||
7: "title.class.inherited"
|
||||
}
|
||||
},
|
||||
// class Car
|
||||
{
|
||||
match: [
|
||||
/class/,
|
||||
/\s+/,
|
||||
IDENT_RE$1
|
||||
],
|
||||
scope: {
|
||||
1: "keyword",
|
||||
3: "title.class"
|
||||
}
|
||||
},
|
||||
|
||||
]
|
||||
};
|
||||
|
||||
const CLASS_REFERENCE = {
|
||||
relevance: 0,
|
||||
match:
|
||||
regex.either(
|
||||
// Hard coded exceptions
|
||||
/\bJSON/,
|
||||
// Float32Array, OutT
|
||||
/\b[A-Z][a-z]+([A-Z][a-z]*|\d)*/,
|
||||
// CSSFactory, CSSFactoryT
|
||||
/\b[A-Z]{2,}([A-Z][a-z]+|\d)+([A-Z][a-z]*)*/,
|
||||
// FPs, FPsT
|
||||
/\b[A-Z]{2,}[a-z]+([A-Z][a-z]+|\d)*([A-Z][a-z]*)*/,
|
||||
// P
|
||||
// single letters are not highlighted
|
||||
// BLAH
|
||||
// this will be flagged as a UPPER_CASE_CONSTANT instead
|
||||
),
|
||||
className: "title.class",
|
||||
keywords: {
|
||||
_: [
|
||||
// se we still get relevance credit for JS library classes
|
||||
...TYPES,
|
||||
...ERROR_TYPES
|
||||
]
|
||||
}
|
||||
};
|
||||
|
||||
const USE_STRICT = {
|
||||
label: "use_strict",
|
||||
className: 'meta',
|
||||
relevance: 10,
|
||||
begin: /^\s*['"]use (strict|asm)['"]/
|
||||
};
|
||||
|
||||
const FUNCTION_DEFINITION = {
|
||||
variants: [
|
||||
{
|
||||
match: [
|
||||
/function/,
|
||||
/\s+/,
|
||||
IDENT_RE$1,
|
||||
/(?=\s*\()/
|
||||
]
|
||||
},
|
||||
// anonymous function
|
||||
{
|
||||
match: [
|
||||
/function/,
|
||||
/\s*(?=\()/
|
||||
]
|
||||
}
|
||||
],
|
||||
className: {
|
||||
1: "keyword",
|
||||
3: "title.function"
|
||||
},
|
||||
label: "func.def",
|
||||
contains: [ PARAMS ],
|
||||
illegal: /%/
|
||||
};
|
||||
|
||||
const UPPER_CASE_CONSTANT = {
|
||||
relevance: 0,
|
||||
match: /\b[A-Z][A-Z_0-9]+\b/,
|
||||
className: "variable.constant"
|
||||
};
|
||||
|
||||
function noneOf(list) {
|
||||
return regex.concat("(?!", list.join("|"), ")");
|
||||
}
|
||||
|
||||
const FUNCTION_CALL = {
|
||||
match: regex.concat(
|
||||
/\b/,
|
||||
noneOf([
|
||||
...BUILT_IN_GLOBALS,
|
||||
"super",
|
||||
"import"
|
||||
]),
|
||||
IDENT_RE$1, regex.lookahead(/\(/)),
|
||||
className: "title.function",
|
||||
relevance: 0
|
||||
};
|
||||
|
||||
const PROPERTY_ACCESS = {
|
||||
begin: regex.concat(/\./, regex.lookahead(
|
||||
regex.concat(IDENT_RE$1, /(?![0-9A-Za-z$_(])/)
|
||||
)),
|
||||
end: IDENT_RE$1,
|
||||
excludeBegin: true,
|
||||
keywords: "prototype",
|
||||
className: "property",
|
||||
relevance: 0
|
||||
};
|
||||
|
||||
const GETTER_OR_SETTER = {
|
||||
match: [
|
||||
/get|set/,
|
||||
/\s+/,
|
||||
IDENT_RE$1,
|
||||
/(?=\()/
|
||||
],
|
||||
className: {
|
||||
1: "keyword",
|
||||
3: "title.function"
|
||||
},
|
||||
contains: [
|
||||
{ // eat to avoid empty params
|
||||
begin: /\(\)/
|
||||
},
|
||||
PARAMS
|
||||
]
|
||||
};
|
||||
|
||||
const FUNC_LEAD_IN_RE = '(\\(' +
|
||||
'[^()]*(\\(' +
|
||||
'[^()]*(\\(' +
|
||||
'[^()]*' +
|
||||
'\\)[^()]*)*' +
|
||||
'\\)[^()]*)*' +
|
||||
'\\)|' + hljs.UNDERSCORE_IDENT_RE + ')\\s*=>';
|
||||
|
||||
const FUNCTION_VARIABLE = {
|
||||
match: [
|
||||
/const|var|let/, /\s+/,
|
||||
IDENT_RE$1, /\s*/,
|
||||
/=\s*/,
|
||||
/(async\s*)?/, // async is optional
|
||||
regex.lookahead(FUNC_LEAD_IN_RE)
|
||||
],
|
||||
keywords: "async",
|
||||
className: {
|
||||
1: "keyword",
|
||||
3: "title.function"
|
||||
},
|
||||
contains: [
|
||||
PARAMS
|
||||
]
|
||||
};
|
||||
|
||||
return {
|
||||
name: 'JavaScript',
|
||||
aliases: ['js', 'jsx', 'mjs', 'cjs'],
|
||||
keywords: KEYWORDS$1,
|
||||
// this will be extended by TypeScript
|
||||
exports: { PARAMS_CONTAINS, CLASS_REFERENCE },
|
||||
illegal: /#(?![$_A-z])/,
|
||||
contains: [
|
||||
hljs.SHEBANG({
|
||||
label: "shebang",
|
||||
binary: "node",
|
||||
relevance: 5
|
||||
}),
|
||||
USE_STRICT,
|
||||
hljs.APOS_STRING_MODE,
|
||||
hljs.QUOTE_STRING_MODE,
|
||||
HTML_TEMPLATE,
|
||||
CSS_TEMPLATE,
|
||||
GRAPHQL_TEMPLATE,
|
||||
TEMPLATE_STRING,
|
||||
COMMENT,
|
||||
// Skip numbers when they are part of a variable name
|
||||
{ match: /\$\d+/ },
|
||||
NUMBER,
|
||||
CLASS_REFERENCE,
|
||||
{
|
||||
className: 'attr',
|
||||
begin: IDENT_RE$1 + regex.lookahead(':'),
|
||||
relevance: 0
|
||||
},
|
||||
FUNCTION_VARIABLE,
|
||||
{ // "value" container
|
||||
begin: '(' + hljs.RE_STARTERS_RE + '|\\b(case|return|throw)\\b)\\s*',
|
||||
keywords: 'return throw case',
|
||||
relevance: 0,
|
||||
contains: [
|
||||
COMMENT,
|
||||
hljs.REGEXP_MODE,
|
||||
{
|
||||
className: 'function',
|
||||
// we have to count the parens to make sure we actually have the
|
||||
// correct bounding ( ) before the =>. There could be any number of
|
||||
// sub-expressions inside also surrounded by parens.
|
||||
begin: FUNC_LEAD_IN_RE,
|
||||
returnBegin: true,
|
||||
end: '\\s*=>',
|
||||
contains: [
|
||||
{
|
||||
className: 'params',
|
||||
variants: [
|
||||
{
|
||||
begin: hljs.UNDERSCORE_IDENT_RE,
|
||||
relevance: 0
|
||||
},
|
||||
{
|
||||
className: null,
|
||||
begin: /\(\s*\)/,
|
||||
skip: true
|
||||
},
|
||||
{
|
||||
begin: /\(/,
|
||||
end: /\)/,
|
||||
excludeBegin: true,
|
||||
excludeEnd: true,
|
||||
keywords: KEYWORDS$1,
|
||||
contains: PARAMS_CONTAINS
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{ // could be a comma delimited list of params to a function call
|
||||
begin: /,/,
|
||||
relevance: 0
|
||||
},
|
||||
{
|
||||
match: /\s+/,
|
||||
relevance: 0
|
||||
},
|
||||
{ // JSX
|
||||
variants: [
|
||||
{ begin: FRAGMENT.begin, end: FRAGMENT.end },
|
||||
{ match: XML_SELF_CLOSING },
|
||||
{
|
||||
begin: XML_TAG.begin,
|
||||
// we carefully check the opening tag to see if it truly
|
||||
// is a tag and not a false positive
|
||||
'on:begin': XML_TAG.isTrulyOpeningTag,
|
||||
end: XML_TAG.end
|
||||
}
|
||||
],
|
||||
subLanguage: 'xml',
|
||||
contains: [
|
||||
{
|
||||
begin: XML_TAG.begin,
|
||||
end: XML_TAG.end,
|
||||
skip: true,
|
||||
contains: ['self']
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
},
|
||||
FUNCTION_DEFINITION,
|
||||
{
|
||||
// prevent this from getting swallowed up by function
|
||||
// since they appear "function like"
|
||||
beginKeywords: "while if switch catch for"
|
||||
},
|
||||
{
|
||||
// we have to count the parens to make sure we actually have the correct
|
||||
// bounding ( ). There could be any number of sub-expressions inside
|
||||
// also surrounded by parens.
|
||||
begin: '\\b(?!function)' + hljs.UNDERSCORE_IDENT_RE +
|
||||
'\\(' + // first parens
|
||||
'[^()]*(\\(' +
|
||||
'[^()]*(\\(' +
|
||||
'[^()]*' +
|
||||
'\\)[^()]*)*' +
|
||||
'\\)[^()]*)*' +
|
||||
'\\)\\s*\\{', // end parens
|
||||
returnBegin:true,
|
||||
label: "func.def",
|
||||
contains: [
|
||||
PARAMS,
|
||||
hljs.inherit(hljs.TITLE_MODE, { begin: IDENT_RE$1, className: "title.function" })
|
||||
]
|
||||
},
|
||||
// catch ... so it won't trigger the property rule below
|
||||
{
|
||||
match: /\.\.\./,
|
||||
relevance: 0
|
||||
},
|
||||
PROPERTY_ACCESS,
|
||||
// hack: prevents detection of keywords in some circumstances
|
||||
// .keyword()
|
||||
// $keyword = x
|
||||
{
|
||||
match: '\\$' + IDENT_RE$1,
|
||||
relevance: 0
|
||||
},
|
||||
{
|
||||
match: [ /\bconstructor(?=\s*\()/ ],
|
||||
className: { 1: "title.function" },
|
||||
contains: [ PARAMS ]
|
||||
},
|
||||
FUNCTION_CALL,
|
||||
UPPER_CASE_CONSTANT,
|
||||
CLASS_OR_EXTENDS,
|
||||
GETTER_OR_SETTER,
|
||||
{
|
||||
match: /\$[(.]/ // relevance booster for a pattern common to JS libs: `$(something)` and `$.something`
|
||||
}
|
||||
]
|
||||
};
|
||||
}
|
||||
|
||||
return javascript;
|
||||
|
||||
})();
|
||||
;
|
||||
export default hljsGrammar;
|
Loading…
Add table
Add a link
Reference in a new issue