(function (Prism) { // see https://github.com/cooklang/spec/blob/main/EBNF.md var single_token_suffix = /(?:(?!\s)[\d$+<=a-zA-Z\x80-\uFFFF])+/.source; var multi_token_infix = /[^{}@#]+/.source; var multi_token_suffix = /\{[^}#@]*\}/.source; var multi_token = multi_token_infix + multi_token_suffix; var timer_units = /(?:h|hours|hrs|m|min|minutes)/.source; var amount_group_impl = { pattern: /\{[^{}]*\}/, inside: { amount: { pattern: /([\{|])[^{}|*%]+/, lookbehind: true, alias: 'number', }, unit: { pattern: /(%)[^}]+/, lookbehind: true, alias: 'symbol', }, 'servings-scaler': { pattern: /\*/, alias: 'operator', }, 'servings-alternative-separator': { pattern: /\|/, alias: 'operator', }, 'unit-separator': { pattern: /(?:%|(\*)%)/, lookbehind: true, alias: 'operator', }, punctuation: /[{}]/, }, }; Prism.languages.cooklang = { comment: { // [- comment -] // -- comment pattern: /\[-[\s\S]*?-\]|--.*/, greedy: true, }, meta: { // >> key: value pattern: />>.*:.*/, inside: { property: { // key: pattern: /(>>\s*)[^\s:](?:[^:]*[^\s:])?/, lookbehind: true, }, }, }, 'cookware-group': { // #...{...}, #... pattern: new RegExp( '#(?:' + multi_token + '|' + single_token_suffix + ')' ), inside: { cookware: { pattern: new RegExp('(^#)(?:' + multi_token_infix + ')'), lookbehind: true, alias: 'variable', }, 'cookware-keyword': { pattern: /^#/, alias: 'keyword', }, 'quantity-group': { pattern: new RegExp(/\{[^{}@#]*\}/), inside: { quantity: { pattern: new RegExp(/(^\{)/.source + multi_token_infix), lookbehind: true, alias: 'number', }, punctuation: /[{}]/, }, }, }, }, 'ingredient-group': { // @...{...}, @... pattern: new RegExp( '@(?:' + multi_token + '|' + single_token_suffix + ')' ), inside: { ingredient: { pattern: new RegExp('(^@)(?:' + multi_token_infix + ')'), lookbehind: true, alias: 'variable', }, 'ingredient-keyword': { pattern: /^@/, alias: 'keyword', }, 'amount-group': amount_group_impl, }, }, 'timer-group': { // ~timer{...} // eslint-disable-next-line regexp/sort-alternatives pattern: /~(?!\s)[^@#~{}]*\{[^{}]*\}/, inside: { timer: { pattern: /(^~)[^{]+/, lookbehind: true, alias: 'variable', }, 'duration-group': { // {...} pattern: /\{[^{}]*\}/, inside: { punctuation: /[{}]/, unit: { pattern: new RegExp(/(%\s*)/.source + timer_units + /\b/.source), lookbehind: true, alias: 'symbol', }, operator: /%/, duration: { pattern: /\d+/, alias: 'number', }, }, }, 'timer-keyword': { pattern: /^~/, alias: 'keyword', }, }, }, }; })(Prism);